Files
gocryptotrader/engine/withdraw_manager.go
dependabot[bot] 179519a3c3 golangci-lint: Bump to v2.0.2 and fix issues (#1871)
* build(deps): Bump golangci/golangci-lint-action from 6 to 7

Bumps [golangci/golangci-lint-action](https://github.com/golangci/golangci-lint-action) from 6 to 7.
- [Release notes](https://github.com/golangci/golangci-lint-action/releases)
- [Commits](https://github.com/golangci/golangci-lint-action/compare/v6...v7)

---
updated-dependencies:
- dependency-name: golangci/golangci-lint-action
  dependency-type: direct:production
  update-type: version-update:semver-major
...

Signed-off-by: dependabot[bot] <support@github.com>

* golangci-lint: Bump to v2 and fix issues

* refactor: remove no longer need ifshort nolint directives, fix test grammar and improve for loop logic

* nits: update order pair handling in tests and improve string replacement logic

---------

Signed-off-by: dependabot[bot] <support@github.com>
Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com>
Co-authored-by: Adrian Gallagher <adrian.gallagher@thrasher.io>
2025-04-02 15:36:05 +11:00

154 lines
4.3 KiB
Go

package engine
import (
"context"
"errors"
"fmt"
"time"
"github.com/thrasher-corp/gocryptotrader/common"
dbwithdraw "github.com/thrasher-corp/gocryptotrader/database/repository/withdraw"
"github.com/thrasher-corp/gocryptotrader/exchanges/asset"
"github.com/thrasher-corp/gocryptotrader/exchanges/currencystate"
"github.com/thrasher-corp/gocryptotrader/log"
"github.com/thrasher-corp/gocryptotrader/portfolio/withdraw"
)
// SetupWithdrawManager creates a new withdraw manager
func SetupWithdrawManager(em iExchangeManager, pm iPortfolioManager, isDryRun bool) (*WithdrawManager, error) {
if em == nil {
return nil, errors.New("nil manager")
}
return &WithdrawManager{
exchangeManager: em,
portfolioManager: pm,
isDryRun: isDryRun,
}, nil
}
// SubmitWithdrawal performs validation and submits a new withdraw request to
// exchange
func (m *WithdrawManager) SubmitWithdrawal(ctx context.Context, req *withdraw.Request) (*withdraw.Response, error) {
if m == nil {
return nil, ErrNilSubsystem
}
if req == nil {
return nil, withdraw.ErrRequestCannotBeNil
}
exch, err := m.exchangeManager.GetExchangeByName(req.Exchange)
if err != nil {
return nil, err
}
resp := &withdraw.Response{
Exchange: withdraw.ExchangeResponse{
Name: req.Exchange,
},
RequestDetails: *req,
}
// Determines if the currency can be withdrawn from the exchange
errF := exch.CanWithdraw(req.Currency, asset.Spot)
if errF != nil && !errors.Is(errF, currencystate.ErrCurrencyStateNotFound) { // Suppress not found error
return nil, errF
}
if m.isDryRun {
log.Warnln(log.Global, "Dry run enabled, no withdrawal request will be submitted or have an event created")
resp.ID = withdraw.DryRunID
resp.Exchange.Status = "dryrun"
resp.Exchange.ID = withdraw.DryRunID.String()
} else {
var ret *withdraw.ExchangeResponse
if req.Type == withdraw.Crypto {
if !m.portfolioManager.IsWhiteListed(req.Crypto.Address) {
return nil, withdraw.ErrStrAddressNotWhiteListed
}
if !m.portfolioManager.IsExchangeSupported(req.Exchange, req.Crypto.Address) {
return nil, withdraw.ErrStrExchangeNotSupportedByAddress
}
}
switch req.Type {
case withdraw.Fiat:
ret, err = exch.WithdrawFiatFunds(ctx, req)
case withdraw.Crypto:
ret, err = exch.WithdrawCryptocurrencyFunds(ctx, req)
default:
return nil, fmt.Errorf("unsupported withdrawal type: %v", req.Type)
}
if err != nil {
resp.Exchange.Status = err.Error()
} else {
resp.Exchange.Status = ret.Status
resp.Exchange.ID = ret.ID
}
}
dbwithdraw.Event(resp)
if err == nil {
withdraw.Cache.Add(resp.ID, resp)
}
return resp, err
}
// WithdrawalEventByID returns a withdrawal request by ID
func (m *WithdrawManager) WithdrawalEventByID(id string) (*withdraw.Response, error) {
if m == nil {
return nil, ErrNilSubsystem
}
if v := withdraw.Cache.Get(id); v != nil {
wdResp, ok := v.(*withdraw.Response)
if !ok {
return nil, common.GetTypeAssertError("*withdraw.Response", v)
}
return wdResp, nil
}
l, err := dbwithdraw.GetEventByUUID(id)
if err != nil {
return nil, fmt.Errorf("%w %v", ErrWithdrawRequestNotFound, id)
}
withdraw.Cache.Add(id, l)
return l, nil
}
// WithdrawalEventByExchange returns a withdrawal request by ID
func (m *WithdrawManager) WithdrawalEventByExchange(exchange string, limit int) ([]*withdraw.Response, error) {
if m == nil {
return nil, ErrNilSubsystem
}
_, err := m.exchangeManager.GetExchangeByName(exchange)
if err != nil {
return nil, err
}
return dbwithdraw.GetEventsByExchange(exchange, limit)
}
// WithdrawEventByDate returns a withdrawal request by ID
func (m *WithdrawManager) WithdrawEventByDate(exchange string, start, end time.Time, limit int) ([]*withdraw.Response, error) {
if m == nil {
return nil, ErrNilSubsystem
}
_, err := m.exchangeManager.GetExchangeByName(exchange)
if err != nil {
return nil, err
}
return dbwithdraw.GetEventsByDate(exchange, start, end, limit)
}
// WithdrawalEventByExchangeID returns a withdrawal request by Exchange ID
func (m *WithdrawManager) WithdrawalEventByExchangeID(exchange, id string) (*withdraw.Response, error) {
if m == nil {
return nil, ErrNilSubsystem
}
_, err := m.exchangeManager.GetExchangeByName(exchange)
if err != nil {
return nil, err
}
return dbwithdraw.GetEventByExchangeID(exchange, id)
}