gpu-compute-chain/x/cosmostest/memdb/biddb.go

125 lines
2.4 KiB
Go

package memdb
import (
"bytes"
"cosmos-test/x/cosmostest/types"
"encoding/gob"
"log"
"math/big"
"github.com/dgraph-io/badger/v3"
)
type bidDB struct {
db *badger.DB
}
var BidDB bidDB
// Mount Db & initialize encoder/decoder
func (b *bidDB) Mount() {
db, err := badger.Open(badger.DefaultOptions("").WithInMemory(true))
if err != nil {
// must force crash here, since db is absolutely required
log.Fatalf("Failed to mount in-memory db: %s", err)
}
b.db = db
// initialize encode/decode stuff
gob.Register([]types.Bid{})
}
// Add a bid to the bid list under specified auction key.
func (b *bidDB) AddBid(auctionId string, bid *types.Bid) error {
k := []byte(auctionId)
err := b.db.Update(func(txn *badger.Txn) error {
var bids []*types.Bid
bidsOld, err := txn.Get(k)
if err == badger.ErrKeyNotFound {
// key not found -> just create a new Bid array
bids = []*types.Bid{}
} else {
if err != nil {
return err
}
// key found -> decode contents to bids
bidsOld.Value(func(val []byte) error {
dec := gob.NewDecoder(bytes.NewReader(val))
if err := dec.Decode(&bids); err != nil {
return err
}
return nil
})
}
// append bid
bids = append(bids, bid)
// encode new list
buf := bytes.NewBuffer(nil)
enc := gob.NewEncoder(buf)
if err := enc.Encode(&bids); err != nil {
return err
}
// set under auction key in db
if err := txn.Set(k, buf.Bytes()); err != nil {
return err
}
return nil
})
return err
}
// Get the highest bid in the list under specified auction key.
func (b *bidDB) GetHighestBid(auctionId string) (*types.Bid, error) {
k := []byte(auctionId)
var bid *types.Bid
err := b.db.View(func(txn *badger.Txn) error {
bidData, err := txn.Get(k)
if err != nil {
return err
}
err = bidData.Value(func(val []byte) error {
var bids []*types.Bid
dec := gob.NewDecoder(bytes.NewReader(val))
if err := dec.Decode(&bids); err != nil {
return err
}
amt := big.NewInt(0)
rAmt := big.NewInt(0)
for _, rBid := range bids {
if bid == nil {
bid = rBid
amt.SetString(rBid.Amount, 10)
} else {
rAmt.SetString(rBid.Amount, 10)
if rAmt.Cmp(amt) == 1 {
bid = rBid
}
}
}
return nil
})
return err
})
return bid, err
}
func (b *bidDB) ClearAuction(auctionId string) error {
k := []byte(auctionId)
err := b.db.Update(func(txn *badger.Txn) error {
return txn.Delete(k)
})
return err
}