app-cloudep-trade-service/internal/repository/user_wallet.go

96 lines
2.5 KiB
Go
Raw Permalink Normal View History

2024-10-29 14:49:47 +00:00
package repository
import (
"app-cloudep-trade-service/internal/domain/repository"
2024-10-31 04:05:22 +00:00
"app-cloudep-trade-service/internal/domain/wallet"
2024-10-29 14:49:47 +00:00
"app-cloudep-trade-service/internal/model"
2024-10-30 11:13:56 +00:00
"context"
2024-10-29 14:49:47 +00:00
"github.com/shopspring/decimal"
2024-10-30 11:13:56 +00:00
"github.com/zeromicro/go-zero/core/stores/sqlx"
2024-10-29 14:49:47 +00:00
)
// 用戶某個幣種餘額
type userLocalWallet struct {
wm model.WalletModel
txConn sqlx.SqlConn
2024-10-30 11:13:56 +00:00
uid string
currency string
2024-10-29 14:49:47 +00:00
// local wallet 相關計算的餘額存在這裡
2024-10-31 04:05:22 +00:00
walletBalance map[wallet.BalanceType]model.Wallet
2024-10-29 14:49:47 +00:00
// local order wallet 相關計算的餘額存在這裡
localOrderBalance map[int64]decimal.Decimal
// local wallet 內所有餘額變化紀錄
transactions []model.WalletJournal
}
2024-10-31 04:05:22 +00:00
// GetBalancesByID 使用 Wallet ID 取得餘額,如果需要上鎖,可以在 option 內加上 tx 以及 lock可以參考 TestBalanceUseCase
2024-10-30 11:13:56 +00:00
func (use *userLocalWallet) GetBalancesByID(ctx context.Context, ids []int64, opts ...repository.WalletOperatorOption) ([]model.Wallet, error) {
o := repository.ApplyOptions(opts...)
tx := use.txConn
if o.Tx != nil {
tx = *o.Tx
}
wallets, err := use.wm.BalancesByIDs(ctx, ids, o.WithLock, tx)
if err != nil {
return nil, err
}
2024-10-31 04:05:22 +00:00
for _, w := range wallets {
use.walletBalance[w.WalletType] = w
2024-10-30 11:13:56 +00:00
}
return wallets, nil
}
// LocalBalance 內存餘額
2024-10-31 04:05:22 +00:00
func (use *userLocalWallet) LocalBalance(BalanceType wallet.BalanceType) decimal.Decimal {
w, ok := use.walletBalance[BalanceType]
2024-10-30 11:13:56 +00:00
if !ok {
return decimal.Zero
}
2024-10-31 04:05:22 +00:00
return w.Balance
2024-10-30 11:13:56 +00:00
}
2024-10-31 04:05:22 +00:00
// Balances 取得餘額如果需要上鎖可以在option 內加上 tx 以及 lock可以參考 TestBalanceUseCase
func (use *userLocalWallet) Balances(ctx context.Context, balanceType []wallet.BalanceType, opts ...repository.WalletOperatorOption) ([]model.Wallet, error) {
2024-10-30 11:13:56 +00:00
o := repository.ApplyOptions(opts...)
tx := use.txConn
if o.Tx != nil {
tx = *o.Tx
}
wallets, err := use.wm.Balances(ctx, model.BalanceReq{
UID: []string{use.uid},
Currency: []string{use.currency},
2024-10-31 04:05:22 +00:00
Kind: balanceType,
2024-10-30 11:13:56 +00:00
}, o.WithLock, tx)
if err != nil {
return nil, err
}
for _, wallet := range wallets {
use.walletBalance[wallet.WalletType] = wallet
}
return wallets, nil
}
func NewUserWalletOperator(uid, currency string, wm model.WalletModel, txConn sqlx.SqlConn) repository.UserWalletOperator {
2024-10-29 14:49:47 +00:00
return &userLocalWallet{
2024-10-30 11:13:56 +00:00
wm: wm,
txConn: txConn,
uid: uid,
currency: currency,
2024-10-29 14:49:47 +00:00
2024-10-31 04:05:22 +00:00
walletBalance: make(map[wallet.BalanceType]model.Wallet, len(wallet.AllBalanceTypes)),
localOrderBalance: make(map[int64]decimal.Decimal, len(wallet.AllBalanceTypes)),
2024-10-29 14:49:47 +00:00
}
}