mirror of
				https://github.com/0glabs/0g-chain.git
				synced 2025-11-04 11:17:28 +00:00 
			
		
		
		
	split keeper file up
This commit is contained in:
		
							parent
							
								
									231aa75774
								
							
						
					
					
						commit
						5618e11990
					
				
							
								
								
									
										297
									
								
								x/auction/keeper/auctions.go
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										297
									
								
								x/auction/keeper/auctions.go
									
									
									
									
									
										Normal file
									
								
							@ -0,0 +1,297 @@
 | 
				
			|||||||
 | 
					package keeper
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					import (
 | 
				
			||||||
 | 
						"fmt"
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						sdk "github.com/cosmos/cosmos-sdk/types"
 | 
				
			||||||
 | 
						"github.com/cosmos/cosmos-sdk/x/supply"
 | 
				
			||||||
 | 
						"github.com/kava-labs/kava/x/auction/types"
 | 
				
			||||||
 | 
					)
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					// StartForwardAuction starts a normal auction.
 | 
				
			||||||
 | 
					func (k Keeper) StartForwardAuction(ctx sdk.Context, seller string, lot sdk.Coin, bidDenom string) (types.ID, sdk.Error) {
 | 
				
			||||||
 | 
						// create auction
 | 
				
			||||||
 | 
						auction := types.NewForwardAuction(seller, lot, bidDenom, ctx.BlockTime().Add(types.DefaultMaxAuctionDuration))
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						// take coins from module account
 | 
				
			||||||
 | 
						err := k.supplyKeeper.SendCoinsFromModuleToModule(ctx, seller, types.ModuleName, sdk.NewCoins(lot))
 | 
				
			||||||
 | 
						if err != nil {
 | 
				
			||||||
 | 
							return 0, err
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
						// store the auction
 | 
				
			||||||
 | 
						auctionID, err := k.storeNewAuction(ctx, auction) // TODO does this need to be a pointer to satisfy the interface?
 | 
				
			||||||
 | 
						if err != nil {
 | 
				
			||||||
 | 
							return 0, err
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
						return auctionID, nil
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					// StartReverseAuction starts an auction where sellers compete by offering decreasing prices.
 | 
				
			||||||
 | 
					func (k Keeper) StartReverseAuction(ctx sdk.Context, buyer string, bid sdk.Coin, initialLot sdk.Coin) (types.ID, sdk.Error) {
 | 
				
			||||||
 | 
						// create auction
 | 
				
			||||||
 | 
						auction := types.NewReverseAuction(buyer, bid, initialLot, ctx.BlockTime().Add(types.DefaultMaxAuctionDuration))
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						// This auction type mints coins at close. Need to check module account has minting privileges to avoid potential err in endblocker.
 | 
				
			||||||
 | 
						macc := k.supplyKeeper.GetModuleAccount(ctx, buyer)
 | 
				
			||||||
 | 
						if !macc.HasPermission(supply.Minter) { // TODO ideally don't want to import supply
 | 
				
			||||||
 | 
							return 0, sdk.ErrInternal("module does not have minting permissions")
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
						// store the auction
 | 
				
			||||||
 | 
						auctionID, err := k.storeNewAuction(ctx, &auction)
 | 
				
			||||||
 | 
						if err != nil {
 | 
				
			||||||
 | 
							return 0, err
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
						return auctionID, nil
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					// StartForwardReverseAuction starts an auction where bidders bid up to a maxBid, then switch to bidding down on price.
 | 
				
			||||||
 | 
					func (k Keeper) StartForwardReverseAuction(ctx sdk.Context, seller string, lot sdk.Coin, maxBid sdk.Coin, otherPerson sdk.AccAddress) (types.ID, sdk.Error) {
 | 
				
			||||||
 | 
						// create auction
 | 
				
			||||||
 | 
						auction := types.NewForwardReverseAuction(seller, lot, ctx.BlockTime().Add(types.DefaultMaxAuctionDuration), maxBid, otherPerson)
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						// take coins from module account
 | 
				
			||||||
 | 
						err := k.supplyKeeper.SendCoinsFromModuleToModule(ctx, seller, types.ModuleName, sdk.Coins{lot})
 | 
				
			||||||
 | 
						if err != nil {
 | 
				
			||||||
 | 
							return 0, err
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
						// store the auction
 | 
				
			||||||
 | 
						auctionID, err := k.storeNewAuction(ctx, &auction)
 | 
				
			||||||
 | 
						if err != nil {
 | 
				
			||||||
 | 
							return 0, err
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
						return auctionID, nil
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					// PlaceBid places a bid on any auction.
 | 
				
			||||||
 | 
					func (k Keeper) PlaceBid(ctx sdk.Context, auctionID types.ID, bidder sdk.AccAddress, bid sdk.Coin, lot sdk.Coin) sdk.Error {
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						// get auction from store
 | 
				
			||||||
 | 
						auction, found := k.GetAuction(ctx, auctionID)
 | 
				
			||||||
 | 
						if !found {
 | 
				
			||||||
 | 
							return sdk.ErrInternal("auction doesn't exist")
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						// check end time
 | 
				
			||||||
 | 
						if ctx.BlockTime().After(auction.GetEndTime()) {
 | 
				
			||||||
 | 
							return sdk.ErrInternal("auction has closed")
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						var err sdk.Error
 | 
				
			||||||
 | 
						var a types.Auction
 | 
				
			||||||
 | 
						switch auc := auction.(type) {
 | 
				
			||||||
 | 
						case types.ForwardAuction:
 | 
				
			||||||
 | 
							a, err = k.PlaceBidForward(ctx, auc, bidder, bid)
 | 
				
			||||||
 | 
							if err != nil {
 | 
				
			||||||
 | 
								return err
 | 
				
			||||||
 | 
							}
 | 
				
			||||||
 | 
						case types.ReverseAuction:
 | 
				
			||||||
 | 
							a, err = k.PlaceBidReverse(ctx, auc, bidder, lot)
 | 
				
			||||||
 | 
							if err != nil {
 | 
				
			||||||
 | 
								return err
 | 
				
			||||||
 | 
							}
 | 
				
			||||||
 | 
						case types.ForwardReverseAuction:
 | 
				
			||||||
 | 
							a, err = k.PlaceBidForwardReverse(ctx, auc, bidder, bid, lot)
 | 
				
			||||||
 | 
							if err != nil {
 | 
				
			||||||
 | 
								return err
 | 
				
			||||||
 | 
							}
 | 
				
			||||||
 | 
						default:
 | 
				
			||||||
 | 
							panic("unrecognized auction type")
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						// store updated auction
 | 
				
			||||||
 | 
						k.SetAuction(ctx, a) // TODO maybe move into above funcs
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						return nil
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					func (k Keeper) PlaceBidForward(ctx sdk.Context, a types.ForwardAuction, bidder sdk.AccAddress, bid sdk.Coin) (types.ForwardAuction, sdk.Error) {
 | 
				
			||||||
 | 
						// Valid New Bid
 | 
				
			||||||
 | 
						if bid.Denom != a.Bid.Denom {
 | 
				
			||||||
 | 
							return a, sdk.ErrInternal("bid denom doesn't match auction")
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
						if !a.Bid.IsLT(bid) { // TODO add minimum bid size
 | 
				
			||||||
 | 
							return a, sdk.ErrInternal("bid not greater than last bid")
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						// Move Coins
 | 
				
			||||||
 | 
						increment := bid.Sub(a.Bid)
 | 
				
			||||||
 | 
						bidAmtToReturn := a.Bid
 | 
				
			||||||
 | 
						if bidder.Equals(a.Bidder) { // catch edge case of someone updating their bid with a low balance
 | 
				
			||||||
 | 
							bidAmtToReturn = sdk.NewInt64Coin(a.Bid.Denom, 0)
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
						err := k.supplyKeeper.SendCoinsFromAccountToModule(ctx, bidder, types.ModuleName, sdk.NewCoins(bidAmtToReturn.Add(increment)))
 | 
				
			||||||
 | 
						if err != nil {
 | 
				
			||||||
 | 
							return a, err
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
						err = k.supplyKeeper.SendCoinsFromModuleToAccount(ctx, types.ModuleName, bidder, sdk.NewCoins(bidAmtToReturn))
 | 
				
			||||||
 | 
						if err != nil {
 | 
				
			||||||
 | 
							return a, err
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
						err = k.supplyKeeper.SendCoinsFromModuleToModule(ctx, types.ModuleName, a.Initiator, sdk.NewCoins(increment)) // increase in bid size is burned
 | 
				
			||||||
 | 
						if err != nil {
 | 
				
			||||||
 | 
							return a, err
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
						err = k.supplyKeeper.BurnCoins(ctx, a.Initiator, sdk.NewCoins(increment))
 | 
				
			||||||
 | 
						if err != nil {
 | 
				
			||||||
 | 
							return a, err
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						// Update Auction
 | 
				
			||||||
 | 
						a.Bidder = bidder
 | 
				
			||||||
 | 
						a.Bid = bid
 | 
				
			||||||
 | 
						// increment timeout
 | 
				
			||||||
 | 
						a.EndTime = earliestTime(ctx.BlockTime().Add(types.DefaultMaxBidDuration), a.MaxEndTime) // TODO write a min func for time types
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						return a, nil
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					func (k Keeper) PlaceBidForwardReverse(ctx sdk.Context, a types.ForwardReverseAuction, bidder sdk.AccAddress, bid sdk.Coin, lot sdk.Coin) (types.ForwardReverseAuction, sdk.Error) {
 | 
				
			||||||
 | 
						// Validate New Bid // TODO min bid increments, make validation code less confusing
 | 
				
			||||||
 | 
						if !a.Bid.IsEqual(a.MaxBid) {
 | 
				
			||||||
 | 
							// Auction is in forward phase, a bid here can put the auction into forward or reverse phases
 | 
				
			||||||
 | 
							if !a.Bid.IsLT(bid) {
 | 
				
			||||||
 | 
								return a, sdk.ErrInternal("auction in forward phase, new bid not higher than last bid")
 | 
				
			||||||
 | 
							}
 | 
				
			||||||
 | 
							if a.MaxBid.IsLT(bid) {
 | 
				
			||||||
 | 
								return a, sdk.ErrInternal("bid higher than max bid")
 | 
				
			||||||
 | 
							}
 | 
				
			||||||
 | 
							if lot.IsNegative() || a.Lot.IsLT(lot) {
 | 
				
			||||||
 | 
								return a, sdk.ErrInternal("lot out of bounds")
 | 
				
			||||||
 | 
							}
 | 
				
			||||||
 | 
							if lot.IsLT(a.Lot) && !bid.IsEqual(a.MaxBid) {
 | 
				
			||||||
 | 
								return a, sdk.ErrInternal("auction cannot enter reverse phase without bidding max bid")
 | 
				
			||||||
 | 
							}
 | 
				
			||||||
 | 
						} else {
 | 
				
			||||||
 | 
							// Auction is in reverse phase, it can never leave reverse phase
 | 
				
			||||||
 | 
							if !bid.IsEqual(a.MaxBid) {
 | 
				
			||||||
 | 
								return a, sdk.ErrInternal("") // not necessary
 | 
				
			||||||
 | 
							}
 | 
				
			||||||
 | 
							if lot.IsNegative() {
 | 
				
			||||||
 | 
								return a, sdk.ErrInternal("can't bid negative amount")
 | 
				
			||||||
 | 
							}
 | 
				
			||||||
 | 
							if !lot.IsLT(a.Lot) {
 | 
				
			||||||
 | 
								return a, sdk.ErrInternal("auction in reverse phase, new bid not less than previous amount")
 | 
				
			||||||
 | 
							}
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						// Move Coins
 | 
				
			||||||
 | 
						bidIncrement := bid.Sub(a.Bid)
 | 
				
			||||||
 | 
						bidAmtToReturn := a.Bid
 | 
				
			||||||
 | 
						lotDecrement := a.Lot.Sub(lot)
 | 
				
			||||||
 | 
						if bidder.Equals(a.Bidder) { // catch edge case of someone updating their bid with a low balance
 | 
				
			||||||
 | 
							bidAmtToReturn = sdk.NewInt64Coin(a.Bid.Denom, 0)
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
						err := k.supplyKeeper.SendCoinsFromAccountToModule(ctx, bidder, types.ModuleName, sdk.NewCoins(bidAmtToReturn.Add(bidIncrement)))
 | 
				
			||||||
 | 
						if err != nil {
 | 
				
			||||||
 | 
							return a, err
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
						err = k.supplyKeeper.SendCoinsFromModuleToAccount(ctx, types.ModuleName, bidder, sdk.NewCoins(bidAmtToReturn))
 | 
				
			||||||
 | 
						if err != nil {
 | 
				
			||||||
 | 
							return a, err
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
						err = k.supplyKeeper.SendCoinsFromModuleToModule(ctx, types.ModuleName, a.Initiator, sdk.NewCoins(bidIncrement))
 | 
				
			||||||
 | 
						if err != nil {
 | 
				
			||||||
 | 
							return a, err
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
						err = k.supplyKeeper.SendCoinsFromModuleToAccount(ctx, types.ModuleName, a.OtherPerson, sdk.NewCoins(lotDecrement))
 | 
				
			||||||
 | 
						if err != nil {
 | 
				
			||||||
 | 
							return a, err
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						// Update Auction
 | 
				
			||||||
 | 
						a.Bidder = bidder
 | 
				
			||||||
 | 
						a.Lot = lot
 | 
				
			||||||
 | 
						a.Bid = bid
 | 
				
			||||||
 | 
						// increment timeout
 | 
				
			||||||
 | 
						a.EndTime = earliestTime(ctx.BlockTime().Add(types.DefaultMaxBidDuration), a.MaxEndTime)
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						return types.ForwardReverseAuction{}, nil
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					func (k Keeper) PlaceBidReverse(ctx sdk.Context, a types.ReverseAuction, bidder sdk.AccAddress, lot sdk.Coin) (types.ReverseAuction, sdk.Error) {
 | 
				
			||||||
 | 
						// Validate New Bid
 | 
				
			||||||
 | 
						if lot.Denom != a.Lot.Denom {
 | 
				
			||||||
 | 
							return a, sdk.ErrInternal("lot denom doesn't match auction")
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
						if lot.IsNegative() {
 | 
				
			||||||
 | 
							return a, sdk.ErrInternal("lot less than 0")
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
						if !lot.IsLT(a.Lot) { // TODO add min bid decrements
 | 
				
			||||||
 | 
							return a, sdk.ErrInternal("lot not smaller than last lot")
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						// Move Coins
 | 
				
			||||||
 | 
						bidAmtToReturn := a.Bid
 | 
				
			||||||
 | 
						if bidder.Equals(a.Bidder) { // catch edge case of someone updating their bid with a low balance
 | 
				
			||||||
 | 
							bidAmtToReturn = sdk.NewInt64Coin(a.Bid.Denom, 0)
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
						err := k.supplyKeeper.SendCoinsFromAccountToModule(ctx, bidder, types.ModuleName, sdk.NewCoins(bidAmtToReturn))
 | 
				
			||||||
 | 
						if err != nil {
 | 
				
			||||||
 | 
							return a, err
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
						err = k.supplyKeeper.SendCoinsFromModuleToAccount(ctx, types.ModuleName, bidder, sdk.NewCoins(bidAmtToReturn))
 | 
				
			||||||
 | 
						if err != nil {
 | 
				
			||||||
 | 
							return a, err
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						// Update Auction
 | 
				
			||||||
 | 
						a.Bidder = bidder
 | 
				
			||||||
 | 
						a.Lot = lot
 | 
				
			||||||
 | 
						// increment timeout
 | 
				
			||||||
 | 
						a.EndTime = earliestTime(ctx.BlockTime().Add(types.DefaultMaxBidDuration), a.MaxEndTime)
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						return a, nil
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					// CloseAuction closes an auction and distributes funds to the highest bidder.
 | 
				
			||||||
 | 
					func (k Keeper) CloseAuction(ctx sdk.Context, auctionID types.ID) sdk.Error {
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						// get the auction from the store
 | 
				
			||||||
 | 
						auction, found := k.GetAuction(ctx, auctionID)
 | 
				
			||||||
 | 
						if !found {
 | 
				
			||||||
 | 
							return sdk.ErrInternal("auction doesn't exist")
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
						// error if auction has not reached the end time
 | 
				
			||||||
 | 
						if ctx.BlockTime().Before(auction.GetEndTime()) {
 | 
				
			||||||
 | 
							return sdk.ErrInternal(fmt.Sprintf("auction can't be closed as curent block time (%v) is under auction end time (%v)", ctx.BlockTime(), auction.GetEndTime()))
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						// payout to the last bidder
 | 
				
			||||||
 | 
						var err sdk.Error
 | 
				
			||||||
 | 
						switch auc := auction.(type) {
 | 
				
			||||||
 | 
						case types.ForwardAuction, types.ForwardReverseAuction:
 | 
				
			||||||
 | 
							err = k.PayoutAuctionLot(ctx, auc)
 | 
				
			||||||
 | 
							if err != nil {
 | 
				
			||||||
 | 
								return err
 | 
				
			||||||
 | 
							}
 | 
				
			||||||
 | 
						case types.ReverseAuction:
 | 
				
			||||||
 | 
							err = k.MintAndPayoutAuctionLot(ctx, auc)
 | 
				
			||||||
 | 
							if err != nil {
 | 
				
			||||||
 | 
								return err
 | 
				
			||||||
 | 
							}
 | 
				
			||||||
 | 
						default:
 | 
				
			||||||
 | 
							panic("unrecognized auction type")
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						// Delete auction from store (and queue)
 | 
				
			||||||
 | 
						k.DeleteAuction(ctx, auctionID)
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						return nil
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					func (k Keeper) MintAndPayoutAuctionLot(ctx sdk.Context, a types.ReverseAuction) sdk.Error {
 | 
				
			||||||
 | 
						err := k.supplyKeeper.MintCoins(ctx, a.Initiator, sdk.NewCoins(a.Lot))
 | 
				
			||||||
 | 
						if err != nil {
 | 
				
			||||||
 | 
							return err
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
						err = k.supplyKeeper.SendCoinsFromModuleToAccount(ctx, a.Initiator, a.Bidder, sdk.NewCoins(a.Lot))
 | 
				
			||||||
 | 
						if err != nil {
 | 
				
			||||||
 | 
							return err
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
						return nil
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					func (k Keeper) PayoutAuctionLot(ctx sdk.Context, a types.Auction) sdk.Error {
 | 
				
			||||||
 | 
						// TODO this function is responsible for the addition of GetBidder and GetLot to auction interface. Could be split in to two funcs that operate on concrete auction types
 | 
				
			||||||
 | 
						err := k.supplyKeeper.SendCoinsFromModuleToAccount(ctx, types.ModuleName, a.GetBidder(), sdk.NewCoins(a.GetLot()))
 | 
				
			||||||
 | 
						if err != nil {
 | 
				
			||||||
 | 
							return err
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
						return nil
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
@ -1,14 +1,9 @@
 | 
				
			|||||||
package keeper
 | 
					package keeper
 | 
				
			||||||
 | 
					
 | 
				
			||||||
import (
 | 
					import (
 | 
				
			||||||
	"bytes"
 | 
					 | 
				
			||||||
	"fmt"
 | 
					 | 
				
			||||||
	"time"
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
	"github.com/cosmos/cosmos-sdk/codec"
 | 
						"github.com/cosmos/cosmos-sdk/codec"
 | 
				
			||||||
	sdk "github.com/cosmos/cosmos-sdk/types"
 | 
						sdk "github.com/cosmos/cosmos-sdk/types"
 | 
				
			||||||
	"github.com/cosmos/cosmos-sdk/x/params/subspace"
 | 
						"github.com/cosmos/cosmos-sdk/x/params/subspace"
 | 
				
			||||||
	"github.com/cosmos/cosmos-sdk/x/supply"
 | 
					 | 
				
			||||||
 | 
					
 | 
				
			||||||
	"github.com/kava-labs/kava/x/auction/types"
 | 
						"github.com/kava-labs/kava/x/auction/types"
 | 
				
			||||||
)
 | 
					)
 | 
				
			||||||
@ -30,469 +25,3 @@ func NewKeeper(cdc *codec.Codec, storeKey sdk.StoreKey, supplyKeeper types.Suppl
 | 
				
			|||||||
		paramSubspace: paramstore.WithKeyTable(types.ParamKeyTable()),
 | 
							paramSubspace: paramstore.WithKeyTable(types.ParamKeyTable()),
 | 
				
			||||||
	}
 | 
						}
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					 | 
				
			||||||
// StartForwardAuction starts a normal auction. Known as flap in maker.
 | 
					 | 
				
			||||||
func (k Keeper) StartForwardAuction(ctx sdk.Context, seller string, lot sdk.Coin, bidDenom string) (types.ID, sdk.Error) {
 | 
					 | 
				
			||||||
	// create auction
 | 
					 | 
				
			||||||
	auction := types.NewForwardAuction(seller, lot, bidDenom, ctx.BlockTime().Add(types.DefaultMaxAuctionDuration))
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
	// take coins from module account
 | 
					 | 
				
			||||||
	err := k.supplyKeeper.SendCoinsFromModuleToModule(ctx, seller, types.ModuleName, sdk.NewCoins(lot))
 | 
					 | 
				
			||||||
	if err != nil {
 | 
					 | 
				
			||||||
		return 0, err
 | 
					 | 
				
			||||||
	}
 | 
					 | 
				
			||||||
	// store the auction
 | 
					 | 
				
			||||||
	auctionID, err := k.storeNewAuction(ctx, auction) // TODO does this need to be a pointer to satisfy the interface?
 | 
					 | 
				
			||||||
	if err != nil {
 | 
					 | 
				
			||||||
		return 0, err
 | 
					 | 
				
			||||||
	}
 | 
					 | 
				
			||||||
	return auctionID, nil
 | 
					 | 
				
			||||||
}
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
// StartReverseAuction starts an auction where sellers compete by offering decreasing prices. Known as flop in maker.
 | 
					 | 
				
			||||||
func (k Keeper) StartReverseAuction(ctx sdk.Context, buyer string, bid sdk.Coin, initialLot sdk.Coin) (types.ID, sdk.Error) {
 | 
					 | 
				
			||||||
	// create auction
 | 
					 | 
				
			||||||
	auction := types.NewReverseAuction(buyer, bid, initialLot, ctx.BlockTime().Add(types.DefaultMaxAuctionDuration))
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
	// This auction type mints coins at close. Need to check module account has minting privileges to avoid potential err in endblocker.
 | 
					 | 
				
			||||||
	macc := k.supplyKeeper.GetModuleAccount(ctx, buyer)
 | 
					 | 
				
			||||||
	if !macc.HasPermission(supply.Minter) { // TODO ideally don't want to import supply
 | 
					 | 
				
			||||||
		return 0, sdk.ErrInternal("module does not have minting permissions")
 | 
					 | 
				
			||||||
	}
 | 
					 | 
				
			||||||
	// store the auction
 | 
					 | 
				
			||||||
	auctionID, err := k.storeNewAuction(ctx, &auction)
 | 
					 | 
				
			||||||
	if err != nil {
 | 
					 | 
				
			||||||
		return 0, err
 | 
					 | 
				
			||||||
	}
 | 
					 | 
				
			||||||
	return auctionID, nil
 | 
					 | 
				
			||||||
}
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
// StartForwardReverseAuction starts an auction where bidders bid up to a maxBid, then switch to bidding down on price. Known as flip in maker.
 | 
					 | 
				
			||||||
func (k Keeper) StartForwardReverseAuction(ctx sdk.Context, seller string, lot sdk.Coin, maxBid sdk.Coin, otherPerson sdk.AccAddress) (types.ID, sdk.Error) {
 | 
					 | 
				
			||||||
	// create auction
 | 
					 | 
				
			||||||
	auction := types.NewForwardReverseAuction(seller, lot, ctx.BlockTime().Add(types.DefaultMaxAuctionDuration), maxBid, otherPerson)
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
	// take coins from module account
 | 
					 | 
				
			||||||
	err := k.supplyKeeper.SendCoinsFromModuleToModule(ctx, seller, types.ModuleName, sdk.Coins{lot})
 | 
					 | 
				
			||||||
	if err != nil {
 | 
					 | 
				
			||||||
		return 0, err
 | 
					 | 
				
			||||||
	}
 | 
					 | 
				
			||||||
	// store the auction
 | 
					 | 
				
			||||||
	auctionID, err := k.storeNewAuction(ctx, &auction)
 | 
					 | 
				
			||||||
	if err != nil {
 | 
					 | 
				
			||||||
		return 0, err
 | 
					 | 
				
			||||||
	}
 | 
					 | 
				
			||||||
	return auctionID, nil
 | 
					 | 
				
			||||||
}
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
// set an auction in the store, adding a new ID, and setting indexes
 | 
					 | 
				
			||||||
func (k Keeper) storeNewAuction(ctx sdk.Context, auction types.Auction) (types.ID, sdk.Error) {
 | 
					 | 
				
			||||||
	// get ID
 | 
					 | 
				
			||||||
	newAuctionID, err := k.getNextAuctionID(ctx)
 | 
					 | 
				
			||||||
	if err != nil {
 | 
					 | 
				
			||||||
		return 0, err
 | 
					 | 
				
			||||||
	}
 | 
					 | 
				
			||||||
	// set ID
 | 
					 | 
				
			||||||
	auction.SetID(newAuctionID)
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
	// store auction
 | 
					 | 
				
			||||||
	k.SetAuction(ctx, auction)
 | 
					 | 
				
			||||||
	k.incrementNextAuctionID(ctx)
 | 
					 | 
				
			||||||
	return newAuctionID, nil
 | 
					 | 
				
			||||||
}
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
// PlaceBid places a bid on any auction.
 | 
					 | 
				
			||||||
func (k Keeper) PlaceBid(ctx sdk.Context, auctionID types.ID, bidder sdk.AccAddress, bid sdk.Coin, lot sdk.Coin) sdk.Error {
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
	// get auction from store
 | 
					 | 
				
			||||||
	auction, found := k.GetAuction(ctx, auctionID)
 | 
					 | 
				
			||||||
	if !found {
 | 
					 | 
				
			||||||
		return sdk.ErrInternal("auction doesn't exist")
 | 
					 | 
				
			||||||
	}
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
	// check end time
 | 
					 | 
				
			||||||
	if ctx.BlockTime().After(auction.GetEndTime()) {
 | 
					 | 
				
			||||||
		return sdk.ErrInternal("auction has closed")
 | 
					 | 
				
			||||||
	}
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
	var err sdk.Error
 | 
					 | 
				
			||||||
	var a types.Auction
 | 
					 | 
				
			||||||
	switch auc := auction.(type) {
 | 
					 | 
				
			||||||
	case types.ForwardAuction:
 | 
					 | 
				
			||||||
		a, err = k.PlaceBidForward(ctx, auc, bidder, bid)
 | 
					 | 
				
			||||||
		if err != nil {
 | 
					 | 
				
			||||||
			return err
 | 
					 | 
				
			||||||
		}
 | 
					 | 
				
			||||||
	case types.ReverseAuction:
 | 
					 | 
				
			||||||
		a, err = k.PlaceBidReverse(ctx, auc, bidder, lot)
 | 
					 | 
				
			||||||
		if err != nil {
 | 
					 | 
				
			||||||
			return err
 | 
					 | 
				
			||||||
		}
 | 
					 | 
				
			||||||
	case types.ForwardReverseAuction:
 | 
					 | 
				
			||||||
		a, err = k.PlaceBidForwardReverse(ctx, auc, bidder, bid, lot)
 | 
					 | 
				
			||||||
		if err != nil {
 | 
					 | 
				
			||||||
			return err
 | 
					 | 
				
			||||||
		}
 | 
					 | 
				
			||||||
	default:
 | 
					 | 
				
			||||||
		panic("unrecognized auction type")
 | 
					 | 
				
			||||||
	}
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
	// store updated auction
 | 
					 | 
				
			||||||
	k.SetAuction(ctx, a) // TODO maybe move into above funcs
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
	return nil
 | 
					 | 
				
			||||||
}
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
func (k Keeper) PlaceBidForward(ctx sdk.Context, a types.ForwardAuction, bidder sdk.AccAddress, bid sdk.Coin) (types.ForwardAuction, sdk.Error) {
 | 
					 | 
				
			||||||
	// Valid New Bid
 | 
					 | 
				
			||||||
	if bid.Denom != a.Bid.Denom {
 | 
					 | 
				
			||||||
		return a, sdk.ErrInternal("bid denom doesn't match auction")
 | 
					 | 
				
			||||||
	}
 | 
					 | 
				
			||||||
	if !a.Bid.IsLT(bid) { // TODO add minimum bid size
 | 
					 | 
				
			||||||
		return a, sdk.ErrInternal("bid not greater than last bid")
 | 
					 | 
				
			||||||
	}
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
	// Move Coins
 | 
					 | 
				
			||||||
	increment := bid.Sub(a.Bid)
 | 
					 | 
				
			||||||
	bidAmtToReturn := a.Bid
 | 
					 | 
				
			||||||
	if bidder.Equals(a.Bidder) { // catch edge case of someone updating their bid with a low balance
 | 
					 | 
				
			||||||
		bidAmtToReturn = sdk.NewInt64Coin(a.Bid.Denom, 0)
 | 
					 | 
				
			||||||
	}
 | 
					 | 
				
			||||||
	err := k.supplyKeeper.SendCoinsFromAccountToModule(ctx, bidder, types.ModuleName, sdk.NewCoins(bidAmtToReturn.Add(increment)))
 | 
					 | 
				
			||||||
	if err != nil {
 | 
					 | 
				
			||||||
		return a, err
 | 
					 | 
				
			||||||
	}
 | 
					 | 
				
			||||||
	err = k.supplyKeeper.SendCoinsFromModuleToAccount(ctx, types.ModuleName, bidder, sdk.NewCoins(bidAmtToReturn))
 | 
					 | 
				
			||||||
	if err != nil {
 | 
					 | 
				
			||||||
		return a, err
 | 
					 | 
				
			||||||
	}
 | 
					 | 
				
			||||||
	err = k.supplyKeeper.SendCoinsFromModuleToModule(ctx, types.ModuleName, a.Initiator, sdk.NewCoins(increment)) // increase in bid size is burned
 | 
					 | 
				
			||||||
	if err != nil {
 | 
					 | 
				
			||||||
		return a, err
 | 
					 | 
				
			||||||
	}
 | 
					 | 
				
			||||||
	err = k.supplyKeeper.BurnCoins(ctx, a.Initiator, sdk.NewCoins(increment))
 | 
					 | 
				
			||||||
	if err != nil {
 | 
					 | 
				
			||||||
		return a, err
 | 
					 | 
				
			||||||
	}
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
	// Update Auction
 | 
					 | 
				
			||||||
	a.Bidder = bidder
 | 
					 | 
				
			||||||
	a.Bid = bid
 | 
					 | 
				
			||||||
	// increment timeout
 | 
					 | 
				
			||||||
	a.EndTime = earliestTime(ctx.BlockTime().Add(types.DefaultMaxBidDuration), a.MaxEndTime) // TODO write a min func for time types
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
	return a, nil
 | 
					 | 
				
			||||||
}
 | 
					 | 
				
			||||||
func (k Keeper) PlaceBidForwardReverse(ctx sdk.Context, a types.ForwardReverseAuction, bidder sdk.AccAddress, bid sdk.Coin, lot sdk.Coin) (types.ForwardReverseAuction, sdk.Error) {
 | 
					 | 
				
			||||||
	// Validate New Bid // TODO min bid increments, make validation code less confusing
 | 
					 | 
				
			||||||
	if !a.Bid.IsEqual(a.MaxBid) {
 | 
					 | 
				
			||||||
		// Auction is in forward phase, a bid here can put the auction into forward or reverse phases
 | 
					 | 
				
			||||||
		if !a.Bid.IsLT(bid) {
 | 
					 | 
				
			||||||
			return a, sdk.ErrInternal("auction in forward phase, new bid not higher than last bid")
 | 
					 | 
				
			||||||
		}
 | 
					 | 
				
			||||||
		if a.MaxBid.IsLT(bid) {
 | 
					 | 
				
			||||||
			return a, sdk.ErrInternal("bid higher than max bid")
 | 
					 | 
				
			||||||
		}
 | 
					 | 
				
			||||||
		if lot.IsNegative() || a.Lot.IsLT(lot) {
 | 
					 | 
				
			||||||
			return a, sdk.ErrInternal("lot out of bounds")
 | 
					 | 
				
			||||||
		}
 | 
					 | 
				
			||||||
		if lot.IsLT(a.Lot) && !bid.IsEqual(a.MaxBid) {
 | 
					 | 
				
			||||||
			return a, sdk.ErrInternal("auction cannot enter reverse phase without bidding max bid")
 | 
					 | 
				
			||||||
		}
 | 
					 | 
				
			||||||
	} else {
 | 
					 | 
				
			||||||
		// Auction is in reverse phase, it can never leave reverse phase
 | 
					 | 
				
			||||||
		if !bid.IsEqual(a.MaxBid) {
 | 
					 | 
				
			||||||
			return a, sdk.ErrInternal("") // not necessary
 | 
					 | 
				
			||||||
		}
 | 
					 | 
				
			||||||
		if lot.IsNegative() {
 | 
					 | 
				
			||||||
			return a, sdk.ErrInternal("can't bid negative amount")
 | 
					 | 
				
			||||||
		}
 | 
					 | 
				
			||||||
		if !lot.IsLT(a.Lot) {
 | 
					 | 
				
			||||||
			return a, sdk.ErrInternal("auction in reverse phase, new bid not less than previous amount")
 | 
					 | 
				
			||||||
		}
 | 
					 | 
				
			||||||
	}
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
	// Move Coins
 | 
					 | 
				
			||||||
	bidIncrement := bid.Sub(a.Bid)
 | 
					 | 
				
			||||||
	bidAmtToReturn := a.Bid
 | 
					 | 
				
			||||||
	lotDecrement := a.Lot.Sub(lot)
 | 
					 | 
				
			||||||
	if bidder.Equals(a.Bidder) { // catch edge case of someone updating their bid with a low balance
 | 
					 | 
				
			||||||
		bidAmtToReturn = sdk.NewInt64Coin(a.Bid.Denom, 0)
 | 
					 | 
				
			||||||
	}
 | 
					 | 
				
			||||||
	err := k.supplyKeeper.SendCoinsFromAccountToModule(ctx, bidder, types.ModuleName, sdk.NewCoins(bidAmtToReturn.Add(bidIncrement)))
 | 
					 | 
				
			||||||
	if err != nil {
 | 
					 | 
				
			||||||
		return a, err
 | 
					 | 
				
			||||||
	}
 | 
					 | 
				
			||||||
	err = k.supplyKeeper.SendCoinsFromModuleToAccount(ctx, types.ModuleName, bidder, sdk.NewCoins(bidAmtToReturn))
 | 
					 | 
				
			||||||
	if err != nil {
 | 
					 | 
				
			||||||
		return a, err
 | 
					 | 
				
			||||||
	}
 | 
					 | 
				
			||||||
	err = k.supplyKeeper.SendCoinsFromModuleToModule(ctx, types.ModuleName, a.Initiator, sdk.NewCoins(bidIncrement))
 | 
					 | 
				
			||||||
	if err != nil {
 | 
					 | 
				
			||||||
		return a, err
 | 
					 | 
				
			||||||
	}
 | 
					 | 
				
			||||||
	err = k.supplyKeeper.SendCoinsFromModuleToAccount(ctx, types.ModuleName, a.OtherPerson, sdk.NewCoins(lotDecrement))
 | 
					 | 
				
			||||||
	if err != nil {
 | 
					 | 
				
			||||||
		return a, err
 | 
					 | 
				
			||||||
	}
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
	// Update Auction
 | 
					 | 
				
			||||||
	a.Bidder = bidder
 | 
					 | 
				
			||||||
	a.Lot = lot
 | 
					 | 
				
			||||||
	a.Bid = bid
 | 
					 | 
				
			||||||
	// increment timeout
 | 
					 | 
				
			||||||
	a.EndTime = earliestTime(ctx.BlockTime().Add(types.DefaultMaxBidDuration), a.MaxEndTime)
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
	return types.ForwardReverseAuction{}, nil
 | 
					 | 
				
			||||||
}
 | 
					 | 
				
			||||||
func (k Keeper) PlaceBidReverse(ctx sdk.Context, a types.ReverseAuction, bidder sdk.AccAddress, lot sdk.Coin) (types.ReverseAuction, sdk.Error) {
 | 
					 | 
				
			||||||
	// Validate New Bid
 | 
					 | 
				
			||||||
	if lot.Denom != a.Lot.Denom {
 | 
					 | 
				
			||||||
		return a, sdk.ErrInternal("lot denom doesn't match auction")
 | 
					 | 
				
			||||||
	}
 | 
					 | 
				
			||||||
	if lot.IsNegative() {
 | 
					 | 
				
			||||||
		return a, sdk.ErrInternal("lot less than 0")
 | 
					 | 
				
			||||||
	}
 | 
					 | 
				
			||||||
	if !lot.IsLT(a.Lot) { // TODO add min bid decrements
 | 
					 | 
				
			||||||
		return a, sdk.ErrInternal("lot not smaller than last lot")
 | 
					 | 
				
			||||||
	}
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
	// Move Coins
 | 
					 | 
				
			||||||
	bidAmtToReturn := a.Bid
 | 
					 | 
				
			||||||
	if bidder.Equals(a.Bidder) { // catch edge case of someone updating their bid with a low balance
 | 
					 | 
				
			||||||
		bidAmtToReturn = sdk.NewInt64Coin(a.Bid.Denom, 0)
 | 
					 | 
				
			||||||
	}
 | 
					 | 
				
			||||||
	err := k.supplyKeeper.SendCoinsFromAccountToModule(ctx, bidder, types.ModuleName, sdk.NewCoins(bidAmtToReturn))
 | 
					 | 
				
			||||||
	if err != nil {
 | 
					 | 
				
			||||||
		return a, err
 | 
					 | 
				
			||||||
	}
 | 
					 | 
				
			||||||
	err = k.supplyKeeper.SendCoinsFromModuleToAccount(ctx, types.ModuleName, bidder, sdk.NewCoins(bidAmtToReturn))
 | 
					 | 
				
			||||||
	if err != nil {
 | 
					 | 
				
			||||||
		return a, err
 | 
					 | 
				
			||||||
	}
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
	// Update Auction
 | 
					 | 
				
			||||||
	a.Bidder = bidder
 | 
					 | 
				
			||||||
	a.Lot = lot
 | 
					 | 
				
			||||||
	// increment timeout
 | 
					 | 
				
			||||||
	a.EndTime = earliestTime(ctx.BlockTime().Add(types.DefaultMaxBidDuration), a.MaxEndTime)
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
	return a, nil
 | 
					 | 
				
			||||||
}
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
// CloseAuction closes an auction and distributes funds to the highest bidder.
 | 
					 | 
				
			||||||
func (k Keeper) CloseAuction(ctx sdk.Context, auctionID types.ID) sdk.Error {
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
	// get the auction from the store
 | 
					 | 
				
			||||||
	auction, found := k.GetAuction(ctx, auctionID)
 | 
					 | 
				
			||||||
	if !found {
 | 
					 | 
				
			||||||
		return sdk.ErrInternal("auction doesn't exist")
 | 
					 | 
				
			||||||
	}
 | 
					 | 
				
			||||||
	// error if auction has not reached the end time
 | 
					 | 
				
			||||||
	if ctx.BlockTime().Before(auction.GetEndTime()) {
 | 
					 | 
				
			||||||
		return sdk.ErrInternal(fmt.Sprintf("auction can't be closed as curent block time (%v) is under auction end time (%v)", ctx.BlockTime(), auction.GetEndTime()))
 | 
					 | 
				
			||||||
	}
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
	// payout to the last bidder
 | 
					 | 
				
			||||||
	var err sdk.Error
 | 
					 | 
				
			||||||
	switch auc := auction.(type) {
 | 
					 | 
				
			||||||
	case types.ForwardAuction, types.ForwardReverseAuction:
 | 
					 | 
				
			||||||
		err = k.PayoutAuctionLot(ctx, auc)
 | 
					 | 
				
			||||||
		if err != nil {
 | 
					 | 
				
			||||||
			return err
 | 
					 | 
				
			||||||
		}
 | 
					 | 
				
			||||||
	case types.ReverseAuction:
 | 
					 | 
				
			||||||
		err = k.MintAndPayoutAuctionLot(ctx, auc)
 | 
					 | 
				
			||||||
		if err != nil {
 | 
					 | 
				
			||||||
			return err
 | 
					 | 
				
			||||||
		}
 | 
					 | 
				
			||||||
	default:
 | 
					 | 
				
			||||||
		panic("unrecognized auction type")
 | 
					 | 
				
			||||||
	}
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
	// Delete auction from store (and queue)
 | 
					 | 
				
			||||||
	k.DeleteAuction(ctx, auctionID)
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
	return nil
 | 
					 | 
				
			||||||
}
 | 
					 | 
				
			||||||
func (k Keeper) MintAndPayoutAuctionLot(ctx sdk.Context, a types.ReverseAuction) sdk.Error {
 | 
					 | 
				
			||||||
	err := k.supplyKeeper.MintCoins(ctx, a.Initiator, sdk.NewCoins(a.Lot))
 | 
					 | 
				
			||||||
	if err != nil {
 | 
					 | 
				
			||||||
		return err
 | 
					 | 
				
			||||||
	}
 | 
					 | 
				
			||||||
	err = k.supplyKeeper.SendCoinsFromModuleToAccount(ctx, a.Initiator, a.Bidder, sdk.NewCoins(a.Lot))
 | 
					 | 
				
			||||||
	if err != nil {
 | 
					 | 
				
			||||||
		return err
 | 
					 | 
				
			||||||
	}
 | 
					 | 
				
			||||||
	return nil
 | 
					 | 
				
			||||||
}
 | 
					 | 
				
			||||||
func (k Keeper) PayoutAuctionLot(ctx sdk.Context, a types.Auction) sdk.Error {
 | 
					 | 
				
			||||||
	err := k.supplyKeeper.SendCoinsFromModuleToAccount(ctx, types.ModuleName, a.GetBidder(), sdk.NewCoins(a.GetLot()))
 | 
					 | 
				
			||||||
	if err != nil {
 | 
					 | 
				
			||||||
		return err
 | 
					 | 
				
			||||||
	}
 | 
					 | 
				
			||||||
	return nil
 | 
					 | 
				
			||||||
}
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
// ---------- Store methods ----------
 | 
					 | 
				
			||||||
// Use these to add and remove auction from the store.
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
// getNextAuctionID gets the next available global AuctionID
 | 
					 | 
				
			||||||
func (k Keeper) getNextAuctionID(ctx sdk.Context) (types.ID, sdk.Error) {
 | 
					 | 
				
			||||||
	// get next ID from store
 | 
					 | 
				
			||||||
	store := ctx.KVStore(k.storeKey)
 | 
					 | 
				
			||||||
	bz := store.Get(k.getNextAuctionIDKey())
 | 
					 | 
				
			||||||
	if bz == nil {
 | 
					 | 
				
			||||||
		// if not found, set the id at 0
 | 
					 | 
				
			||||||
		bz = k.cdc.MustMarshalBinaryLengthPrefixed(types.ID(0))
 | 
					 | 
				
			||||||
		store.Set(k.getNextAuctionIDKey(), bz)
 | 
					 | 
				
			||||||
		// TODO Set auction ID in genesis
 | 
					 | 
				
			||||||
		//return 0, ErrInvalidGenesis(keeper.codespace, "InitialProposalID never set")
 | 
					 | 
				
			||||||
	}
 | 
					 | 
				
			||||||
	var auctionID types.ID
 | 
					 | 
				
			||||||
	k.cdc.MustUnmarshalBinaryLengthPrefixed(bz, &auctionID)
 | 
					 | 
				
			||||||
	return auctionID, nil
 | 
					 | 
				
			||||||
}
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
// incrementNextAuctionID increments the global ID in the store by 1
 | 
					 | 
				
			||||||
func (k Keeper) incrementNextAuctionID(ctx sdk.Context) sdk.Error {
 | 
					 | 
				
			||||||
	// get next ID from store
 | 
					 | 
				
			||||||
	store := ctx.KVStore(k.storeKey)
 | 
					 | 
				
			||||||
	bz := store.Get(k.getNextAuctionIDKey())
 | 
					 | 
				
			||||||
	if bz == nil {
 | 
					 | 
				
			||||||
		panic("initial auctionID never set in genesis")
 | 
					 | 
				
			||||||
		//return 0, ErrInvalidGenesis(keeper.codespace, "InitialProposalID never set") // TODO
 | 
					 | 
				
			||||||
	}
 | 
					 | 
				
			||||||
	var auctionID types.ID
 | 
					 | 
				
			||||||
	k.cdc.MustUnmarshalBinaryLengthPrefixed(bz, &auctionID)
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
	// increment the stored next ID
 | 
					 | 
				
			||||||
	bz = k.cdc.MustMarshalBinaryLengthPrefixed(auctionID + 1)
 | 
					 | 
				
			||||||
	store.Set(k.getNextAuctionIDKey(), bz)
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
	return nil
 | 
					 | 
				
			||||||
}
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
// SetAuction puts the auction into the database and adds it to the queue
 | 
					 | 
				
			||||||
// it overwrites any pre-existing auction with same ID
 | 
					 | 
				
			||||||
func (k Keeper) SetAuction(ctx sdk.Context, auction types.Auction) {
 | 
					 | 
				
			||||||
	// remove the auction from the queue if it is already in there
 | 
					 | 
				
			||||||
	existingAuction, found := k.GetAuction(ctx, auction.GetID())
 | 
					 | 
				
			||||||
	if found {
 | 
					 | 
				
			||||||
		k.removeFromQueue(ctx, existingAuction.GetEndTime(), existingAuction.GetID())
 | 
					 | 
				
			||||||
	}
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
	// store auction
 | 
					 | 
				
			||||||
	store := ctx.KVStore(k.storeKey)
 | 
					 | 
				
			||||||
	bz := k.cdc.MustMarshalBinaryLengthPrefixed(auction)
 | 
					 | 
				
			||||||
	store.Set(k.getAuctionKey(auction.GetID()), bz)
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
	// add to the queue
 | 
					 | 
				
			||||||
	k.InsertIntoQueue(ctx, auction.GetEndTime(), auction.GetID())
 | 
					 | 
				
			||||||
}
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
// getAuction gets an auction from the store by auctionID
 | 
					 | 
				
			||||||
func (k Keeper) GetAuction(ctx sdk.Context, auctionID types.ID) (types.Auction, bool) {
 | 
					 | 
				
			||||||
	var auction types.Auction
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
	store := ctx.KVStore(k.storeKey)
 | 
					 | 
				
			||||||
	bz := store.Get(k.getAuctionKey(auctionID))
 | 
					 | 
				
			||||||
	if bz == nil {
 | 
					 | 
				
			||||||
		return auction, false
 | 
					 | 
				
			||||||
	}
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
	k.cdc.MustUnmarshalBinaryLengthPrefixed(bz, &auction)
 | 
					 | 
				
			||||||
	return auction, true
 | 
					 | 
				
			||||||
}
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
// DeleteAuction removes an auction from the store without any validation
 | 
					 | 
				
			||||||
func (k Keeper) DeleteAuction(ctx sdk.Context, auctionID types.ID) {
 | 
					 | 
				
			||||||
	// remove from queue
 | 
					 | 
				
			||||||
	auction, found := k.GetAuction(ctx, auctionID)
 | 
					 | 
				
			||||||
	if found {
 | 
					 | 
				
			||||||
		k.removeFromQueue(ctx, auction.GetEndTime(), auctionID)
 | 
					 | 
				
			||||||
	}
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
	// delete auction
 | 
					 | 
				
			||||||
	store := ctx.KVStore(k.storeKey)
 | 
					 | 
				
			||||||
	store.Delete(k.getAuctionKey(auctionID))
 | 
					 | 
				
			||||||
}
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
// ---------- Queue and key methods ----------
 | 
					 | 
				
			||||||
// These are lower level function used by the store methods above.
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
func (k Keeper) getNextAuctionIDKey() []byte {
 | 
					 | 
				
			||||||
	return []byte("nextAuctionID")
 | 
					 | 
				
			||||||
}
 | 
					 | 
				
			||||||
func (k Keeper) getAuctionKey(auctionID types.ID) []byte {
 | 
					 | 
				
			||||||
	return []byte(fmt.Sprintf("auctions:%d", auctionID))
 | 
					 | 
				
			||||||
}
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
// Inserts a AuctionID into the queue at endTime
 | 
					 | 
				
			||||||
func (k Keeper) InsertIntoQueue(ctx sdk.Context, endTime time.Time, auctionID types.ID) {
 | 
					 | 
				
			||||||
	// get the store
 | 
					 | 
				
			||||||
	store := ctx.KVStore(k.storeKey)
 | 
					 | 
				
			||||||
	// marshal thing to be inserted
 | 
					 | 
				
			||||||
	bz := k.cdc.MustMarshalBinaryLengthPrefixed(auctionID)
 | 
					 | 
				
			||||||
	// store it
 | 
					 | 
				
			||||||
	store.Set(
 | 
					 | 
				
			||||||
		getQueueElementKey(endTime, auctionID),
 | 
					 | 
				
			||||||
		bz,
 | 
					 | 
				
			||||||
	)
 | 
					 | 
				
			||||||
}
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
// removes an auctionID from the queue
 | 
					 | 
				
			||||||
func (k Keeper) removeFromQueue(ctx sdk.Context, endTime time.Time, auctionID types.ID) {
 | 
					 | 
				
			||||||
	store := ctx.KVStore(k.storeKey)
 | 
					 | 
				
			||||||
	store.Delete(getQueueElementKey(endTime, auctionID))
 | 
					 | 
				
			||||||
}
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
// Returns an iterator for all the auctions in the queue that expire by endTime
 | 
					 | 
				
			||||||
func (k Keeper) GetQueueIterator(ctx sdk.Context, endTime time.Time) sdk.Iterator { // TODO rename to "getAuctionsByExpiry" ?
 | 
					 | 
				
			||||||
	// get store
 | 
					 | 
				
			||||||
	store := ctx.KVStore(k.storeKey)
 | 
					 | 
				
			||||||
	// get an interator
 | 
					 | 
				
			||||||
	return store.Iterator(
 | 
					 | 
				
			||||||
		queueKeyPrefix, // start key
 | 
					 | 
				
			||||||
		sdk.PrefixEndBytes(getQueueElementKeyPrefix(endTime)), // end key (apparently exclusive but tests suggested otherwise)
 | 
					 | 
				
			||||||
	)
 | 
					 | 
				
			||||||
}
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
// GetAuctionIterator returns an iterator over all auctions in the store
 | 
					 | 
				
			||||||
func (k Keeper) GetAuctionIterator(ctx sdk.Context) sdk.Iterator {
 | 
					 | 
				
			||||||
	store := ctx.KVStore(k.storeKey)
 | 
					 | 
				
			||||||
	return sdk.KVStorePrefixIterator(store, nil)
 | 
					 | 
				
			||||||
}
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
var queueKeyPrefix = []byte("queue")
 | 
					 | 
				
			||||||
var keyDelimiter = []byte(":")
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
// Returns half a key for an auctionID in the queue, it missed the id off the end
 | 
					 | 
				
			||||||
func getQueueElementKeyPrefix(endTime time.Time) []byte {
 | 
					 | 
				
			||||||
	return bytes.Join([][]byte{
 | 
					 | 
				
			||||||
		queueKeyPrefix,
 | 
					 | 
				
			||||||
		sdk.Uint64ToBigEndian(uint64(endTime)), // TODO check this gives correct ordering
 | 
					 | 
				
			||||||
	}, keyDelimiter)
 | 
					 | 
				
			||||||
}
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
// Returns the key for an auctionID in the queue
 | 
					 | 
				
			||||||
func getQueueElementKey(endTime time.Time, auctionID types.ID) []byte {
 | 
					 | 
				
			||||||
	return bytes.Join([][]byte{
 | 
					 | 
				
			||||||
		queueKeyPrefix,
 | 
					 | 
				
			||||||
		sdk.Uint64ToBigEndian(uint64(endTime)), // TODO check this gives correct ordering
 | 
					 | 
				
			||||||
		sdk.Uint64ToBigEndian(uint64(auctionID)),
 | 
					 | 
				
			||||||
	}, keyDelimiter)
 | 
					 | 
				
			||||||
}
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
// GetAuctionID returns the id from an input Auction
 | 
					 | 
				
			||||||
func (k Keeper) DecodeAuctionID(ctx sdk.Context, idBytes []byte) types.ID {
 | 
					 | 
				
			||||||
	var auctionID types.ID
 | 
					 | 
				
			||||||
	k.cdc.MustUnmarshalBinaryLengthPrefixed(idBytes, &auctionID)
 | 
					 | 
				
			||||||
	return auctionID
 | 
					 | 
				
			||||||
}
 | 
					 | 
				
			||||||
 | 
					 | 
				
			||||||
func (k Keeper) DecodeAuction(ctx sdk.Context, auctionBytes []byte) types.Auction {
 | 
					 | 
				
			||||||
	var auction types.Auction
 | 
					 | 
				
			||||||
	k.cdc.MustUnmarshalBinaryBare(auctionBytes, &auction)
 | 
					 | 
				
			||||||
	return auction
 | 
					 | 
				
			||||||
}
 | 
					 | 
				
			||||||
 | 
				
			|||||||
							
								
								
									
										187
									
								
								x/auction/keeper/store.go
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										187
									
								
								x/auction/keeper/store.go
									
									
									
									
									
										Normal file
									
								
							@ -0,0 +1,187 @@
 | 
				
			|||||||
 | 
					package keeper
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					import (
 | 
				
			||||||
 | 
						"bytes"
 | 
				
			||||||
 | 
						"fmt"
 | 
				
			||||||
 | 
						"time"
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						sdk "github.com/cosmos/cosmos-sdk/types"
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						"github.com/kava-labs/kava/x/auction/types"
 | 
				
			||||||
 | 
					)
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					// set an auction in the store, adding a new ID, and setting indexes
 | 
				
			||||||
 | 
					func (k Keeper) storeNewAuction(ctx sdk.Context, auction types.Auction) (types.ID, sdk.Error) {
 | 
				
			||||||
 | 
						// get ID
 | 
				
			||||||
 | 
						newAuctionID, err := k.getNextAuctionID(ctx)
 | 
				
			||||||
 | 
						if err != nil {
 | 
				
			||||||
 | 
							return 0, err
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
						// set ID
 | 
				
			||||||
 | 
						auction.SetID(newAuctionID)
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						// store auction
 | 
				
			||||||
 | 
						k.SetAuction(ctx, auction)
 | 
				
			||||||
 | 
						k.incrementNextAuctionID(ctx)
 | 
				
			||||||
 | 
						return newAuctionID, nil
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					// getNextAuctionID gets the next available global AuctionID
 | 
				
			||||||
 | 
					func (k Keeper) getNextAuctionID(ctx sdk.Context) (types.ID, sdk.Error) {
 | 
				
			||||||
 | 
						// get next ID from store
 | 
				
			||||||
 | 
						store := ctx.KVStore(k.storeKey)
 | 
				
			||||||
 | 
						bz := store.Get(k.getNextAuctionIDKey())
 | 
				
			||||||
 | 
						if bz == nil {
 | 
				
			||||||
 | 
							// if not found, set the id at 0
 | 
				
			||||||
 | 
							bz = k.cdc.MustMarshalBinaryLengthPrefixed(types.ID(0))
 | 
				
			||||||
 | 
							store.Set(k.getNextAuctionIDKey(), bz)
 | 
				
			||||||
 | 
							// TODO Set auction ID in genesis
 | 
				
			||||||
 | 
							//return 0, ErrInvalidGenesis(keeper.codespace, "InitialProposalID never set")
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
						var auctionID types.ID
 | 
				
			||||||
 | 
						k.cdc.MustUnmarshalBinaryLengthPrefixed(bz, &auctionID)
 | 
				
			||||||
 | 
						return auctionID, nil
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					// incrementNextAuctionID increments the global ID in the store by 1
 | 
				
			||||||
 | 
					func (k Keeper) incrementNextAuctionID(ctx sdk.Context) sdk.Error {
 | 
				
			||||||
 | 
						// get next ID from store
 | 
				
			||||||
 | 
						store := ctx.KVStore(k.storeKey)
 | 
				
			||||||
 | 
						bz := store.Get(k.getNextAuctionIDKey())
 | 
				
			||||||
 | 
						if bz == nil {
 | 
				
			||||||
 | 
							panic("initial auctionID never set in genesis")
 | 
				
			||||||
 | 
							//return 0, ErrInvalidGenesis(keeper.codespace, "InitialProposalID never set") // TODO
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
						var auctionID types.ID
 | 
				
			||||||
 | 
						k.cdc.MustUnmarshalBinaryLengthPrefixed(bz, &auctionID)
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						// increment the stored next ID
 | 
				
			||||||
 | 
						bz = k.cdc.MustMarshalBinaryLengthPrefixed(auctionID + 1)
 | 
				
			||||||
 | 
						store.Set(k.getNextAuctionIDKey(), bz)
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						return nil
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					// SetAuction puts the auction into the database and adds it to the queue
 | 
				
			||||||
 | 
					// it overwrites any pre-existing auction with same ID
 | 
				
			||||||
 | 
					func (k Keeper) SetAuction(ctx sdk.Context, auction types.Auction) {
 | 
				
			||||||
 | 
						// remove the auction from the queue if it is already in there
 | 
				
			||||||
 | 
						existingAuction, found := k.GetAuction(ctx, auction.GetID())
 | 
				
			||||||
 | 
						if found {
 | 
				
			||||||
 | 
							k.removeFromQueue(ctx, existingAuction.GetEndTime(), existingAuction.GetID())
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						// store auction
 | 
				
			||||||
 | 
						store := ctx.KVStore(k.storeKey)
 | 
				
			||||||
 | 
						bz := k.cdc.MustMarshalBinaryLengthPrefixed(auction)
 | 
				
			||||||
 | 
						store.Set(k.getAuctionKey(auction.GetID()), bz)
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						// add to the queue
 | 
				
			||||||
 | 
						k.InsertIntoQueue(ctx, auction.GetEndTime(), auction.GetID())
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					// getAuction gets an auction from the store by auctionID
 | 
				
			||||||
 | 
					func (k Keeper) GetAuction(ctx sdk.Context, auctionID types.ID) (types.Auction, bool) {
 | 
				
			||||||
 | 
						var auction types.Auction
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						store := ctx.KVStore(k.storeKey)
 | 
				
			||||||
 | 
						bz := store.Get(k.getAuctionKey(auctionID))
 | 
				
			||||||
 | 
						if bz == nil {
 | 
				
			||||||
 | 
							return auction, false
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						k.cdc.MustUnmarshalBinaryLengthPrefixed(bz, &auction)
 | 
				
			||||||
 | 
						return auction, true
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					// DeleteAuction removes an auction from the store without any validation
 | 
				
			||||||
 | 
					func (k Keeper) DeleteAuction(ctx sdk.Context, auctionID types.ID) {
 | 
				
			||||||
 | 
						// remove from queue
 | 
				
			||||||
 | 
						auction, found := k.GetAuction(ctx, auctionID)
 | 
				
			||||||
 | 
						if found {
 | 
				
			||||||
 | 
							k.removeFromQueue(ctx, auction.GetEndTime(), auctionID)
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						// delete auction
 | 
				
			||||||
 | 
						store := ctx.KVStore(k.storeKey)
 | 
				
			||||||
 | 
						store.Delete(k.getAuctionKey(auctionID))
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					// ---------- Queue and key methods ----------
 | 
				
			||||||
 | 
					// These are lower level function used by the store methods above.
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					func (k Keeper) getNextAuctionIDKey() []byte {
 | 
				
			||||||
 | 
						return []byte("nextAuctionID")
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					func (k Keeper) getAuctionKey(auctionID types.ID) []byte {
 | 
				
			||||||
 | 
						return []byte(fmt.Sprintf("auctions:%d", auctionID))
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					// Inserts a AuctionID into the queue at endTime
 | 
				
			||||||
 | 
					func (k Keeper) InsertIntoQueue(ctx sdk.Context, endTime time.Time, auctionID types.ID) {
 | 
				
			||||||
 | 
						// get the store
 | 
				
			||||||
 | 
						store := ctx.KVStore(k.storeKey)
 | 
				
			||||||
 | 
						// marshal thing to be inserted
 | 
				
			||||||
 | 
						bz := k.cdc.MustMarshalBinaryLengthPrefixed(auctionID)
 | 
				
			||||||
 | 
						// store it
 | 
				
			||||||
 | 
						store.Set(
 | 
				
			||||||
 | 
							getQueueElementKey(endTime, auctionID),
 | 
				
			||||||
 | 
							bz,
 | 
				
			||||||
 | 
						)
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					// removes an auctionID from the queue
 | 
				
			||||||
 | 
					func (k Keeper) removeFromQueue(ctx sdk.Context, endTime time.Time, auctionID types.ID) {
 | 
				
			||||||
 | 
						store := ctx.KVStore(k.storeKey)
 | 
				
			||||||
 | 
						store.Delete(getQueueElementKey(endTime, auctionID))
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					// Returns an iterator for all the auctions in the queue that expire by endTime
 | 
				
			||||||
 | 
					func (k Keeper) GetQueueIterator(ctx sdk.Context, endTime time.Time) sdk.Iterator { // TODO rename to "getAuctionsByExpiry" ?
 | 
				
			||||||
 | 
						// get store
 | 
				
			||||||
 | 
						store := ctx.KVStore(k.storeKey)
 | 
				
			||||||
 | 
						// get an interator
 | 
				
			||||||
 | 
						return store.Iterator(
 | 
				
			||||||
 | 
							queueKeyPrefix, // start key
 | 
				
			||||||
 | 
							sdk.PrefixEndBytes(getQueueElementKeyPrefix(endTime)), // end key (apparently exclusive but tests suggested otherwise)
 | 
				
			||||||
 | 
						)
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					// GetAuctionIterator returns an iterator over all auctions in the store
 | 
				
			||||||
 | 
					func (k Keeper) GetAuctionIterator(ctx sdk.Context) sdk.Iterator {
 | 
				
			||||||
 | 
						store := ctx.KVStore(k.storeKey)
 | 
				
			||||||
 | 
						return sdk.KVStorePrefixIterator(store, nil)
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					var queueKeyPrefix = []byte("queue")
 | 
				
			||||||
 | 
					var keyDelimiter = []byte(":")
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					// Returns half a key for an auctionID in the queue, it missed the id off the end
 | 
				
			||||||
 | 
					func getQueueElementKeyPrefix(endTime time.Time) []byte {
 | 
				
			||||||
 | 
						return bytes.Join([][]byte{
 | 
				
			||||||
 | 
							queueKeyPrefix,
 | 
				
			||||||
 | 
							sdk.Uint64ToBigEndian(uint64(endTime)), // TODO check this gives correct ordering
 | 
				
			||||||
 | 
						}, keyDelimiter)
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					// Returns the key for an auctionID in the queue
 | 
				
			||||||
 | 
					func getQueueElementKey(endTime time.Time, auctionID types.ID) []byte {
 | 
				
			||||||
 | 
						return bytes.Join([][]byte{
 | 
				
			||||||
 | 
							queueKeyPrefix,
 | 
				
			||||||
 | 
							sdk.Uint64ToBigEndian(uint64(endTime)), // TODO check this gives correct ordering
 | 
				
			||||||
 | 
							sdk.Uint64ToBigEndian(uint64(auctionID)),
 | 
				
			||||||
 | 
						}, keyDelimiter)
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					// GetAuctionID returns the id from an input Auction
 | 
				
			||||||
 | 
					func (k Keeper) DecodeAuctionID(ctx sdk.Context, idBytes []byte) types.ID {
 | 
				
			||||||
 | 
						var auctionID types.ID
 | 
				
			||||||
 | 
						k.cdc.MustUnmarshalBinaryLengthPrefixed(idBytes, &auctionID)
 | 
				
			||||||
 | 
						return auctionID
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					func (k Keeper) DecodeAuction(ctx sdk.Context, auctionBytes []byte) types.Auction {
 | 
				
			||||||
 | 
						var auction types.Auction
 | 
				
			||||||
 | 
						k.cdc.MustUnmarshalBinaryBare(auctionBytes, &auction)
 | 
				
			||||||
 | 
						return auction
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
		Loading…
	
		Reference in New Issue
	
	Block a user