mirror of
https://github.com/c9s/bbgo.git
synced 2024-11-21 22:43:52 +00:00
fix go fmt, fix convert.go (the legacy fixedpoint implementation) in all tests
This commit is contained in:
parent
eb70410f80
commit
8648528435
|
@ -7,8 +7,8 @@ import (
|
||||||
"strings"
|
"strings"
|
||||||
"sync"
|
"sync"
|
||||||
|
|
||||||
"github.com/c9s/bbgo/pkg/types"
|
|
||||||
"github.com/c9s/bbgo/pkg/fixedpoint"
|
"github.com/c9s/bbgo/pkg/fixedpoint"
|
||||||
|
"github.com/c9s/bbgo/pkg/types"
|
||||||
)
|
)
|
||||||
|
|
||||||
func zero(a float64) bool {
|
func zero(a float64) bool {
|
||||||
|
@ -57,15 +57,15 @@ type StockDistribution struct {
|
||||||
}
|
}
|
||||||
|
|
||||||
type DistributionStats struct {
|
type DistributionStats struct {
|
||||||
PriceLevels []string `json:"priceLevels"`
|
PriceLevels []string `json:"priceLevels"`
|
||||||
TotalQuantity fixedpoint.Value `json:"totalQuantity"`
|
TotalQuantity fixedpoint.Value `json:"totalQuantity"`
|
||||||
Quantities map[string]fixedpoint.Value `json:"quantities"`
|
Quantities map[string]fixedpoint.Value `json:"quantities"`
|
||||||
Stocks map[string]StockSlice `json:"stocks"`
|
Stocks map[string]StockSlice `json:"stocks"`
|
||||||
}
|
}
|
||||||
|
|
||||||
func (m *StockDistribution) DistributionStats(level int) *DistributionStats {
|
func (m *StockDistribution) DistributionStats(level int) *DistributionStats {
|
||||||
var d = DistributionStats{
|
var d = DistributionStats{
|
||||||
Quantities: map[string]fixedpoint.Value {},
|
Quantities: map[string]fixedpoint.Value{},
|
||||||
Stocks: map[string]StockSlice{},
|
Stocks: map[string]StockSlice{},
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -7,8 +7,8 @@ import (
|
||||||
|
|
||||||
"github.com/stretchr/testify/assert"
|
"github.com/stretchr/testify/assert"
|
||||||
|
|
||||||
"github.com/c9s/bbgo/pkg/types"
|
|
||||||
"github.com/c9s/bbgo/pkg/fixedpoint"
|
"github.com/c9s/bbgo/pkg/fixedpoint"
|
||||||
|
"github.com/c9s/bbgo/pkg/types"
|
||||||
)
|
)
|
||||||
|
|
||||||
func TestStockManager(t *testing.T) {
|
func TestStockManager(t *testing.T) {
|
||||||
|
|
|
@ -39,4 +39,3 @@ func (s *Stream) Connect(ctx context.Context) error {
|
||||||
func (s *Stream) Close() error {
|
func (s *Stream) Close() error {
|
||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -8,4 +8,3 @@ import (
|
||||||
type Context struct {
|
type Context struct {
|
||||||
sync.Mutex
|
sync.Mutex
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -3,4 +3,3 @@ package bbgo
|
||||||
import "errors"
|
import "errors"
|
||||||
|
|
||||||
var ErrSessionAlreadyInitialized = errors.New("session is already initialized")
|
var ErrSessionAlreadyInitialized = errors.New("session is already initialized")
|
||||||
|
|
||||||
|
|
|
@ -8,9 +8,9 @@ import (
|
||||||
"strconv"
|
"strconv"
|
||||||
"strings"
|
"strings"
|
||||||
|
|
||||||
|
"github.com/c9s/bbgo/pkg/fixedpoint"
|
||||||
"github.com/c9s/bbgo/pkg/interact"
|
"github.com/c9s/bbgo/pkg/interact"
|
||||||
"github.com/c9s/bbgo/pkg/types"
|
"github.com/c9s/bbgo/pkg/types"
|
||||||
"github.com/c9s/bbgo/pkg/fixedpoint"
|
|
||||||
)
|
)
|
||||||
|
|
||||||
type PositionCloser interface {
|
type PositionCloser interface {
|
||||||
|
@ -128,7 +128,7 @@ func (it *CoreInteraction) Commands(i *interact.Interact) {
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if kc, ok := reply.(interact.KeyboardController) ; ok {
|
if kc, ok := reply.(interact.KeyboardController); ok {
|
||||||
kc.RemoveKeyboard()
|
kc.RemoveKeyboard()
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -176,7 +176,7 @@ func (it *CoreInteraction) Commands(i *interact.Interact) {
|
||||||
|
|
||||||
if position.Base.IsZero() {
|
if position.Base.IsZero() {
|
||||||
reply.Message("No opened position")
|
reply.Message("No opened position")
|
||||||
if kc, ok := reply.(interact.KeyboardController) ; ok {
|
if kc, ok := reply.(interact.KeyboardController); ok {
|
||||||
kc.RemoveKeyboard()
|
kc.RemoveKeyboard()
|
||||||
}
|
}
|
||||||
return fmt.Errorf("no opened position")
|
return fmt.Errorf("no opened position")
|
||||||
|
@ -197,7 +197,7 @@ func (it *CoreInteraction) Commands(i *interact.Interact) {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
|
||||||
if kc, ok := reply.(interact.KeyboardController) ; ok {
|
if kc, ok := reply.(interact.KeyboardController); ok {
|
||||||
kc.RemoveKeyboard()
|
kc.RemoveKeyboard()
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -11,7 +11,7 @@ type MovingAverageSettings struct {
|
||||||
Interval types.Interval `json:"interval"`
|
Interval types.Interval `json:"interval"`
|
||||||
Window int `json:"window"`
|
Window int `json:"window"`
|
||||||
|
|
||||||
Side *types.SideType `json:"side"`
|
Side *types.SideType `json:"side"`
|
||||||
|
|
||||||
QuantityOrAmount
|
QuantityOrAmount
|
||||||
}
|
}
|
||||||
|
|
|
@ -217,7 +217,7 @@ func (c *BasicRiskController) ProcessOrders(session *ExchangeSession, orders ...
|
||||||
accumulativeQuoteAmount = accumulativeQuoteAmount.Add(notional)
|
accumulativeQuoteAmount = accumulativeQuoteAmount.Add(notional)
|
||||||
|
|
||||||
case types.SideTypeSell:
|
case types.SideTypeSell:
|
||||||
minNotion := market.MinNotional.Mul(increaseFactor)
|
minNotion := market.MinNotional.Mul(increaseFactor)
|
||||||
|
|
||||||
// Critical conditions for placing SELL orders
|
// Critical conditions for placing SELL orders
|
||||||
baseAssetBalance, ok := balances[market.BaseCurrency]
|
baseAssetBalance, ok := balances[market.BaseCurrency]
|
||||||
|
|
|
@ -3,8 +3,8 @@ package bbgo
|
||||||
import (
|
import (
|
||||||
"testing"
|
"testing"
|
||||||
|
|
||||||
"github.com/stretchr/testify/assert"
|
|
||||||
"github.com/c9s/bbgo/pkg/fixedpoint"
|
"github.com/c9s/bbgo/pkg/fixedpoint"
|
||||||
|
"github.com/stretchr/testify/assert"
|
||||||
)
|
)
|
||||||
|
|
||||||
func TestAdjustQuantityByMinAmount(t *testing.T) {
|
func TestAdjustQuantityByMinAmount(t *testing.T) {
|
||||||
|
@ -19,8 +19,8 @@ func TestAdjustQuantityByMinAmount(t *testing.T) {
|
||||||
|
|
||||||
tests := []testcase{
|
tests := []testcase{
|
||||||
{
|
{
|
||||||
name: "amount too small",
|
name: "amount too small",
|
||||||
args: args{
|
args: args{
|
||||||
fixedpoint.MustNewFromString("0.1"),
|
fixedpoint.MustNewFromString("0.1"),
|
||||||
fixedpoint.MustNewFromString("10.0"),
|
fixedpoint.MustNewFromString("10.0"),
|
||||||
fixedpoint.MustNewFromString("10.0"),
|
fixedpoint.MustNewFromString("10.0"),
|
||||||
|
@ -28,8 +28,8 @@ func TestAdjustQuantityByMinAmount(t *testing.T) {
|
||||||
wanted: "1.0",
|
wanted: "1.0",
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
name: "amount equals to min amount",
|
name: "amount equals to min amount",
|
||||||
args: args{
|
args: args{
|
||||||
fixedpoint.MustNewFromString("1.0"),
|
fixedpoint.MustNewFromString("1.0"),
|
||||||
fixedpoint.MustNewFromString("10.0"),
|
fixedpoint.MustNewFromString("10.0"),
|
||||||
fixedpoint.MustNewFromString("10.0"),
|
fixedpoint.MustNewFromString("10.0"),
|
||||||
|
@ -37,8 +37,8 @@ func TestAdjustQuantityByMinAmount(t *testing.T) {
|
||||||
wanted: "1.0",
|
wanted: "1.0",
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
name: "amount is greater than min amount",
|
name: "amount is greater than min amount",
|
||||||
args: args{
|
args: args{
|
||||||
fixedpoint.MustNewFromString("2.0"),
|
fixedpoint.MustNewFromString("2.0"),
|
||||||
fixedpoint.MustNewFromString("10.0"),
|
fixedpoint.MustNewFromString("10.0"),
|
||||||
fixedpoint.MustNewFromString("10.0"),
|
fixedpoint.MustNewFromString("10.0"),
|
||||||
|
|
|
@ -4,7 +4,6 @@ import (
|
||||||
"testing"
|
"testing"
|
||||||
|
|
||||||
"github.com/stretchr/testify/assert"
|
"github.com/stretchr/testify/assert"
|
||||||
|
|
||||||
)
|
)
|
||||||
|
|
||||||
const Delta = 1e-9
|
const Delta = 1e-9
|
||||||
|
@ -200,4 +199,3 @@ func TestPercentageScale(t *testing.T) {
|
||||||
assert.InDelta(t, 100.0, v, Delta)
|
assert.InDelta(t, 100.0, v, Delta)
|
||||||
})
|
})
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -173,8 +173,8 @@ type ExchangeSession struct {
|
||||||
|
|
||||||
// Withdrawal is used for enabling withdrawal functions
|
// Withdrawal is used for enabling withdrawal functions
|
||||||
Withdrawal bool `json:"withdrawal,omitempty" yaml:"withdrawal,omitempty"`
|
Withdrawal bool `json:"withdrawal,omitempty" yaml:"withdrawal,omitempty"`
|
||||||
MakerFeeRate fixedpoint.Value `json:"makerFeeRate,omitempty" yaml:"makerFeeRate,omitempty"`
|
MakerFeeRate fixedpoint.Value `json:"makerFeeRate" yaml:"makerFeeRate"`
|
||||||
TakerFeeRate fixedpoint.Value `json:"takerFeeRate,omitempty" yaml:"takerFeeRate,omitempty"`
|
TakerFeeRate fixedpoint.Value `json:"takerFeeRate" yaml:"takerFeeRate"`
|
||||||
|
|
||||||
PublicOnly bool `json:"publicOnly,omitempty" yaml:"publicOnly"`
|
PublicOnly bool `json:"publicOnly,omitempty" yaml:"publicOnly"`
|
||||||
Margin bool `json:"margin,omitempty" yaml:"margin"`
|
Margin bool `json:"margin,omitempty" yaml:"margin"`
|
||||||
|
|
|
@ -115,7 +115,7 @@ func (c *TrailingStopController) Run(ctx context.Context, session *ExchangeSessi
|
||||||
// if the profit rate is defined, and it is less than our minimum profit rate, we skip stop
|
// if the profit rate is defined, and it is less than our minimum profit rate, we skip stop
|
||||||
if c.MinProfit.Sign() > 0 &&
|
if c.MinProfit.Sign() > 0 &&
|
||||||
closePrice.Compare(c.averageCost) < 0 ||
|
closePrice.Compare(c.averageCost) < 0 ||
|
||||||
changeRate(closePrice, c.averageCost).Compare(c.MinProfit) < 0 {
|
changeRate(closePrice, c.averageCost).Compare(c.MinProfit) < 0 {
|
||||||
return
|
return
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -5,8 +5,8 @@ import (
|
||||||
|
|
||||||
"github.com/stretchr/testify/assert"
|
"github.com/stretchr/testify/assert"
|
||||||
|
|
||||||
"github.com/c9s/bbgo/pkg/types"
|
|
||||||
"github.com/c9s/bbgo/pkg/fixedpoint"
|
"github.com/c9s/bbgo/pkg/fixedpoint"
|
||||||
|
"github.com/c9s/bbgo/pkg/types"
|
||||||
)
|
)
|
||||||
|
|
||||||
func TestTradeCollector_ShouldNotCountDuplicatedTrade(t *testing.T) {
|
func TestTradeCollector_ShouldNotCountDuplicatedTrade(t *testing.T) {
|
||||||
|
@ -31,12 +31,12 @@ func TestTradeCollector_ShouldNotCountDuplicatedTrade(t *testing.T) {
|
||||||
assert.Equal(t, 1, len(collector.tradeStore.Trades()), "should have one trade in the trade store")
|
assert.Equal(t, 1, len(collector.tradeStore.Trades()), "should have one trade in the trade store")
|
||||||
|
|
||||||
orderStore.Add(types.Order{
|
orderStore.Add(types.Order{
|
||||||
SubmitOrder: types.SubmitOrder{
|
SubmitOrder: types.SubmitOrder{
|
||||||
Symbol: "BTCUSDT",
|
Symbol: "BTCUSDT",
|
||||||
Side: types.SideTypeBuy,
|
Side: types.SideTypeBuy,
|
||||||
Type: types.OrderTypeLimit,
|
Type: types.OrderTypeLimit,
|
||||||
Quantity: fixedpoint.One,
|
Quantity: fixedpoint.One,
|
||||||
Price: fixedpoint.NewFromInt(40000),
|
Price: fixedpoint.NewFromInt(40000),
|
||||||
},
|
},
|
||||||
Exchange: types.ExchangeBinance,
|
Exchange: types.ExchangeBinance,
|
||||||
OrderID: 399,
|
OrderID: 399,
|
||||||
|
|
|
@ -283,7 +283,7 @@ func (e *TwapExecution) updateOrder(ctx context.Context) error {
|
||||||
}
|
}
|
||||||
|
|
||||||
func (e *TwapExecution) cancelActiveOrders() {
|
func (e *TwapExecution) cancelActiveOrders() {
|
||||||
gracefulCtx, gracefulCancel := context.WithTimeout(context.TODO(), 30 * time.Second)
|
gracefulCtx, gracefulCancel := context.WithTimeout(context.TODO(), 30*time.Second)
|
||||||
defer gracefulCancel()
|
defer gracefulCancel()
|
||||||
e.activeMakerOrders.GracefulCancel(gracefulCtx, e.Session.Exchange)
|
e.activeMakerOrders.GracefulCancel(gracefulCtx, e.Session.Exchange)
|
||||||
}
|
}
|
||||||
|
|
|
@ -21,15 +21,15 @@ import (
|
||||||
"github.com/c9s/bbgo/pkg/backtest"
|
"github.com/c9s/bbgo/pkg/backtest"
|
||||||
"github.com/c9s/bbgo/pkg/bbgo"
|
"github.com/c9s/bbgo/pkg/bbgo"
|
||||||
"github.com/c9s/bbgo/pkg/cmd/cmdutil"
|
"github.com/c9s/bbgo/pkg/cmd/cmdutil"
|
||||||
|
"github.com/c9s/bbgo/pkg/fixedpoint"
|
||||||
"github.com/c9s/bbgo/pkg/service"
|
"github.com/c9s/bbgo/pkg/service"
|
||||||
"github.com/c9s/bbgo/pkg/types"
|
"github.com/c9s/bbgo/pkg/types"
|
||||||
"github.com/c9s/bbgo/pkg/fixedpoint"
|
|
||||||
)
|
)
|
||||||
|
|
||||||
type BackTestReport struct {
|
type BackTestReport struct {
|
||||||
Symbol string `json:"symbol,omitempty"`
|
Symbol string `json:"symbol,omitempty"`
|
||||||
LastPrice fixedpoint.Value `json:"lastPrice,omitempty"`
|
LastPrice fixedpoint.Value `json:"lastPrice,omitempty"`
|
||||||
StartPrice fixedpoint.Value `json:"startPrice,omitempty"`
|
StartPrice fixedpoint.Value `json:"startPrice,omitempty"`
|
||||||
PnLReport *pnl.AverageCostPnlReport `json:"pnlReport,omitempty"`
|
PnLReport *pnl.AverageCostPnlReport `json:"pnlReport,omitempty"`
|
||||||
InitialBalances types.BalanceMap `json:"initialBalances,omitempty"`
|
InitialBalances types.BalanceMap `json:"initialBalances,omitempty"`
|
||||||
FinalBalances types.BalanceMap `json:"finalBalances,omitempty"`
|
FinalBalances types.BalanceMap `json:"finalBalances,omitempty"`
|
||||||
|
|
|
@ -24,7 +24,6 @@ var balancesCmd = &cobra.Command{
|
||||||
RunE: func(cmd *cobra.Command, args []string) error {
|
RunE: func(cmd *cobra.Command, args []string) error {
|
||||||
ctx := context.Background()
|
ctx := context.Background()
|
||||||
|
|
||||||
|
|
||||||
configFile, err := cmd.Flags().GetString("config")
|
configFile, err := cmd.Flags().GetString("config")
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return err
|
return err
|
||||||
|
@ -39,7 +38,6 @@ var balancesCmd = &cobra.Command{
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
// if config file exists, use the config loaded from the config file.
|
// if config file exists, use the config loaded from the config file.
|
||||||
// otherwise, use a empty config object
|
// otherwise, use a empty config object
|
||||||
var userConfig *bbgo.Config
|
var userConfig *bbgo.Config
|
||||||
|
@ -63,7 +61,6 @@ var balancesCmd = &cobra.Command{
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
if len(sessionName) > 0 {
|
if len(sessionName) > 0 {
|
||||||
session, ok := environ.Session(sessionName)
|
session, ok := environ.Session(sessionName)
|
||||||
if !ok {
|
if !ok {
|
||||||
|
@ -89,7 +86,6 @@ var balancesCmd = &cobra.Command{
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
return nil
|
return nil
|
||||||
},
|
},
|
||||||
}
|
}
|
||||||
|
|
|
@ -14,6 +14,7 @@ import (
|
||||||
_ "github.com/c9s/bbgo/pkg/strategy/pricedrop"
|
_ "github.com/c9s/bbgo/pkg/strategy/pricedrop"
|
||||||
_ "github.com/c9s/bbgo/pkg/strategy/rebalance"
|
_ "github.com/c9s/bbgo/pkg/strategy/rebalance"
|
||||||
_ "github.com/c9s/bbgo/pkg/strategy/schedule"
|
_ "github.com/c9s/bbgo/pkg/strategy/schedule"
|
||||||
|
_ "github.com/c9s/bbgo/pkg/strategy/skeleton"
|
||||||
_ "github.com/c9s/bbgo/pkg/strategy/support"
|
_ "github.com/c9s/bbgo/pkg/strategy/support"
|
||||||
_ "github.com/c9s/bbgo/pkg/strategy/swing"
|
_ "github.com/c9s/bbgo/pkg/strategy/swing"
|
||||||
_ "github.com/c9s/bbgo/pkg/strategy/techsignal"
|
_ "github.com/c9s/bbgo/pkg/strategy/techsignal"
|
||||||
|
@ -22,5 +23,4 @@ import (
|
||||||
_ "github.com/c9s/bbgo/pkg/strategy/xmaker"
|
_ "github.com/c9s/bbgo/pkg/strategy/xmaker"
|
||||||
_ "github.com/c9s/bbgo/pkg/strategy/xnav"
|
_ "github.com/c9s/bbgo/pkg/strategy/xnav"
|
||||||
_ "github.com/c9s/bbgo/pkg/strategy/xpuremaker"
|
_ "github.com/c9s/bbgo/pkg/strategy/xpuremaker"
|
||||||
_ "github.com/c9s/bbgo/pkg/strategy/skeleton"
|
|
||||||
)
|
)
|
||||||
|
|
|
@ -85,7 +85,6 @@ var cancelOrderCmd = &cobra.Command{
|
||||||
|
|
||||||
var sessions = environ.Sessions()
|
var sessions = environ.Sessions()
|
||||||
|
|
||||||
|
|
||||||
if len(sessionName) > 0 {
|
if len(sessionName) > 0 {
|
||||||
ses, ok := environ.Session(sessionName)
|
ses, ok := environ.Session(sessionName)
|
||||||
if !ok {
|
if !ok {
|
||||||
|
|
|
@ -13,7 +13,7 @@ import (
|
||||||
"github.com/c9s/bbgo/pkg/types"
|
"github.com/c9s/bbgo/pkg/types"
|
||||||
)
|
)
|
||||||
|
|
||||||
func NewExchangePublic(exchangeName types.ExchangeName) (types.Exchange, error){
|
func NewExchangePublic(exchangeName types.ExchangeName) (types.Exchange, error) {
|
||||||
return NewExchangeStandard(exchangeName, "", "", "", "")
|
return NewExchangeStandard(exchangeName, "", "", "", "")
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -164,7 +164,6 @@ func runConfig(basectx context.Context, cmd *cobra.Command, userConfig *bbgo.Con
|
||||||
environ.BindSync(userConfig)
|
environ.BindSync(userConfig)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
trader := bbgo.NewTrader(environ)
|
trader := bbgo.NewTrader(environ)
|
||||||
if err := trader.Configure(userConfig); err != nil {
|
if err := trader.Configure(userConfig); err != nil {
|
||||||
return err
|
return err
|
||||||
|
|
|
@ -58,8 +58,6 @@ var SyncCmd = &cobra.Command{
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
sessionName, err := cmd.Flags().GetString("session")
|
sessionName, err := cmd.Flags().GetString("session")
|
||||||
if err != nil {
|
if err != nil {
|
||||||
return err
|
return err
|
||||||
|
|
|
@ -10,8 +10,8 @@ import (
|
||||||
"github.com/spf13/cobra"
|
"github.com/spf13/cobra"
|
||||||
|
|
||||||
"github.com/c9s/bbgo/pkg/bbgo"
|
"github.com/c9s/bbgo/pkg/bbgo"
|
||||||
"github.com/c9s/bbgo/pkg/types"
|
|
||||||
"github.com/c9s/bbgo/pkg/fixedpoint"
|
"github.com/c9s/bbgo/pkg/fixedpoint"
|
||||||
|
"github.com/c9s/bbgo/pkg/types"
|
||||||
)
|
)
|
||||||
|
|
||||||
func init() {
|
func init() {
|
||||||
|
|
|
@ -6,8 +6,8 @@ import (
|
||||||
"github.com/spf13/viper"
|
"github.com/spf13/viper"
|
||||||
|
|
||||||
"github.com/c9s/bbgo/pkg/exchange/ftx"
|
"github.com/c9s/bbgo/pkg/exchange/ftx"
|
||||||
"github.com/c9s/bbgo/pkg/types"
|
|
||||||
"github.com/c9s/bbgo/pkg/fixedpoint"
|
"github.com/c9s/bbgo/pkg/fixedpoint"
|
||||||
|
"github.com/c9s/bbgo/pkg/types"
|
||||||
)
|
)
|
||||||
|
|
||||||
func inQuoteAsset(balances types.BalanceMap, market types.Market, price fixedpoint.Value) fixedpoint.Value {
|
func inQuoteAsset(balances types.BalanceMap, market types.Market, price fixedpoint.Value) fixedpoint.Value {
|
||||||
|
|
|
@ -3,8 +3,8 @@
|
||||||
package fixedpoint
|
package fixedpoint
|
||||||
|
|
||||||
import (
|
import (
|
||||||
|
"bytes"
|
||||||
"database/sql/driver"
|
"database/sql/driver"
|
||||||
"encoding/json"
|
|
||||||
"errors"
|
"errors"
|
||||||
"fmt"
|
"fmt"
|
||||||
"math"
|
"math"
|
||||||
|
@ -57,7 +57,7 @@ func (v Value) Value() (driver.Value, error) {
|
||||||
func (v *Value) Scan(src interface{}) error {
|
func (v *Value) Scan(src interface{}) error {
|
||||||
switch d := src.(type) {
|
switch d := src.(type) {
|
||||||
case int64:
|
case int64:
|
||||||
*v = Value(d)
|
*v = NewFromInt(d)
|
||||||
return nil
|
return nil
|
||||||
|
|
||||||
case float64:
|
case float64:
|
||||||
|
@ -95,7 +95,8 @@ func (v Value) String() string {
|
||||||
}
|
}
|
||||||
|
|
||||||
func (v Value) FormatString(prec int) string {
|
func (v Value) FormatString(prec int) string {
|
||||||
return strconv.FormatFloat(float64(v)/DefaultPow, 'f', prec, 64)
|
result := strconv.FormatFloat(float64(v)/DefaultPow, 'f', prec+1, 64)
|
||||||
|
return result[:len(result)-1]
|
||||||
}
|
}
|
||||||
|
|
||||||
func (v Value) Percentage() string {
|
func (v Value) Percentage() string {
|
||||||
|
@ -109,7 +110,8 @@ func (v Value) FormatPercentage(prec int) string {
|
||||||
if v == 0 {
|
if v == 0 {
|
||||||
return "0"
|
return "0"
|
||||||
}
|
}
|
||||||
return strconv.FormatFloat(float64(v)/DefaultPow*100., 'f', prec, 64) + "%"
|
result := strconv.FormatFloat(float64(v)/DefaultPow*100., 'f', prec+1, 64)
|
||||||
|
return result[:len(result)-1] + "%"
|
||||||
}
|
}
|
||||||
|
|
||||||
func (v Value) SignedPercentage() string {
|
func (v Value) SignedPercentage() string {
|
||||||
|
@ -223,36 +225,21 @@ func (v Value) MarshalJSON() ([]byte, error) {
|
||||||
}
|
}
|
||||||
|
|
||||||
func (v *Value) UnmarshalJSON(data []byte) error {
|
func (v *Value) UnmarshalJSON(data []byte) error {
|
||||||
var a interface{}
|
if bytes.Compare(data, []byte{'n', 'u', 'l', 'l'}) == 0 {
|
||||||
var err = json.Unmarshal(data, &a)
|
*v = Zero
|
||||||
if err != nil {
|
return nil
|
||||||
|
}
|
||||||
|
if len(data) == 0 {
|
||||||
|
*v = Zero
|
||||||
|
return nil
|
||||||
|
}
|
||||||
|
var err error
|
||||||
|
if data[0] == '"' {
|
||||||
|
data = data[1 : len(data)-1]
|
||||||
|
}
|
||||||
|
if *v, err = NewFromString(string(data)); err != nil {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
|
||||||
switch d := a.(type) {
|
|
||||||
case float64:
|
|
||||||
*v = NewFromFloat(d)
|
|
||||||
case float32:
|
|
||||||
*v = NewFromFloat(float64(d))
|
|
||||||
|
|
||||||
case int64:
|
|
||||||
*v = NewFromInt(d)
|
|
||||||
case int:
|
|
||||||
*v = NewFromInt(int64(d))
|
|
||||||
|
|
||||||
case string:
|
|
||||||
v2, err := NewFromString(d)
|
|
||||||
if err != nil {
|
|
||||||
return err
|
|
||||||
}
|
|
||||||
|
|
||||||
*v = v2
|
|
||||||
|
|
||||||
default:
|
|
||||||
return fmt.Errorf("unsupported type: %T %v", d, d)
|
|
||||||
|
|
||||||
}
|
|
||||||
|
|
||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -166,7 +166,7 @@ func NewFromFloat(f float64) Value {
|
||||||
}
|
}
|
||||||
_, e := math.Frexp(f)
|
_, e := math.Frexp(f)
|
||||||
e = int(float32(e) / log2of10)
|
e = int(float32(e) / log2of10)
|
||||||
c := uint64(f / math.Pow(10, float64(e-16)))
|
c := uint64(f/math.Pow10(e-16) + 0.5)
|
||||||
return newNoSignCheck(sign, c, e)
|
return newNoSignCheck(sign, c, e)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -995,8 +995,9 @@ func (v *Value) UnmarshalYAML(unmarshal func(a interface{}) error) (err error) {
|
||||||
return err
|
return err
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// FIXME: should we limit to 8 prec?
|
||||||
func (v Value) MarshalJSON() ([]byte, error) {
|
func (v Value) MarshalJSON() ([]byte, error) {
|
||||||
return []byte(v.String()), nil
|
return []byte(v.FormatString(8)), nil
|
||||||
}
|
}
|
||||||
|
|
||||||
func (v *Value) UnmarshalJSON(data []byte) error {
|
func (v *Value) UnmarshalJSON(data []byte) error {
|
||||||
|
|
|
@ -1,12 +1,12 @@
|
||||||
package indicator
|
package indicator
|
||||||
|
|
||||||
import (
|
import (
|
||||||
|
"encoding/json"
|
||||||
"math"
|
"math"
|
||||||
"testing"
|
"testing"
|
||||||
"encoding/json"
|
|
||||||
|
|
||||||
"github.com/c9s/bbgo/pkg/types"
|
|
||||||
"github.com/c9s/bbgo/pkg/fixedpoint"
|
"github.com/c9s/bbgo/pkg/fixedpoint"
|
||||||
|
"github.com/c9s/bbgo/pkg/types"
|
||||||
)
|
)
|
||||||
|
|
||||||
// generated from:
|
// generated from:
|
||||||
|
@ -1030,7 +1030,7 @@ func Test_calculateEWMA(t *testing.T) {
|
||||||
priceF KLinePriceMapper
|
priceF KLinePriceMapper
|
||||||
window int
|
window int
|
||||||
}
|
}
|
||||||
var input []fixedpoint.Value;
|
var input []fixedpoint.Value
|
||||||
if err := json.Unmarshal(ethusdt5m, &input); err != nil {
|
if err := json.Unmarshal(ethusdt5m, &input); err != nil {
|
||||||
panic(err)
|
panic(err)
|
||||||
}
|
}
|
||||||
|
|
|
@ -1,12 +1,12 @@
|
||||||
package indicator
|
package indicator
|
||||||
|
|
||||||
import (
|
import (
|
||||||
|
"encoding/json"
|
||||||
"math"
|
"math"
|
||||||
"testing"
|
"testing"
|
||||||
"encoding/json"
|
|
||||||
|
|
||||||
"github.com/c9s/bbgo/pkg/types"
|
|
||||||
"github.com/c9s/bbgo/pkg/fixedpoint"
|
"github.com/c9s/bbgo/pkg/fixedpoint"
|
||||||
|
"github.com/c9s/bbgo/pkg/types"
|
||||||
)
|
)
|
||||||
|
|
||||||
/*
|
/*
|
||||||
|
|
|
@ -1,13 +1,13 @@
|
||||||
package indicator
|
package indicator
|
||||||
|
|
||||||
import (
|
import (
|
||||||
"testing"
|
|
||||||
"encoding/json"
|
"encoding/json"
|
||||||
|
"testing"
|
||||||
|
|
||||||
"github.com/stretchr/testify/assert"
|
"github.com/stretchr/testify/assert"
|
||||||
|
|
||||||
"github.com/c9s/bbgo/pkg/types"
|
|
||||||
"github.com/c9s/bbgo/pkg/fixedpoint"
|
"github.com/c9s/bbgo/pkg/fixedpoint"
|
||||||
|
"github.com/c9s/bbgo/pkg/types"
|
||||||
)
|
)
|
||||||
|
|
||||||
const Delta = 1e-9
|
const Delta = 1e-9
|
||||||
|
@ -33,7 +33,7 @@ func Test_calculateOBV(t *testing.T) {
|
||||||
want types.Float64Slice
|
want types.Float64Slice
|
||||||
}{
|
}{
|
||||||
{
|
{
|
||||||
name: "trivial_case",
|
name: "trivial_case",
|
||||||
kLines: buildKLines(
|
kLines: buildKLines(
|
||||||
[]fixedpoint.Value{fixedpoint.Zero}, []fixedpoint.Value{fixedpoint.One},
|
[]fixedpoint.Value{fixedpoint.Zero}, []fixedpoint.Value{fixedpoint.One},
|
||||||
),
|
),
|
||||||
|
@ -53,7 +53,7 @@ func Test_calculateOBV(t *testing.T) {
|
||||||
obv := OBV{IntervalWindow: types.IntervalWindow{Window: tt.window}}
|
obv := OBV{IntervalWindow: types.IntervalWindow{Window: tt.window}}
|
||||||
obv.calculateAndUpdate(tt.kLines)
|
obv.calculateAndUpdate(tt.kLines)
|
||||||
assert.Equal(t, len(obv.Values), len(tt.want))
|
assert.Equal(t, len(obv.Values), len(tt.want))
|
||||||
for i, v := range(obv.Values) {
|
for i, v := range obv.Values {
|
||||||
assert.InDelta(t, v, tt.want[i], Delta)
|
assert.InDelta(t, v, tt.want[i], Delta)
|
||||||
}
|
}
|
||||||
})
|
})
|
||||||
|
|
|
@ -1,13 +1,13 @@
|
||||||
package indicator
|
package indicator
|
||||||
|
|
||||||
import (
|
import (
|
||||||
|
"encoding/json"
|
||||||
"math"
|
"math"
|
||||||
"testing"
|
"testing"
|
||||||
"time"
|
"time"
|
||||||
"encoding/json"
|
|
||||||
|
|
||||||
"github.com/c9s/bbgo/pkg/types"
|
|
||||||
"github.com/c9s/bbgo/pkg/fixedpoint"
|
"github.com/c9s/bbgo/pkg/fixedpoint"
|
||||||
|
"github.com/c9s/bbgo/pkg/types"
|
||||||
)
|
)
|
||||||
|
|
||||||
/*
|
/*
|
||||||
|
|
|
@ -1,13 +1,14 @@
|
||||||
package indicator
|
package indicator
|
||||||
|
|
||||||
import (
|
import (
|
||||||
|
"encoding/json"
|
||||||
"math"
|
"math"
|
||||||
"testing"
|
"testing"
|
||||||
"encoding/json"
|
|
||||||
|
|
||||||
"github.com/c9s/bbgo/pkg/types"
|
|
||||||
"github.com/c9s/bbgo/pkg/fixedpoint"
|
"github.com/c9s/bbgo/pkg/fixedpoint"
|
||||||
|
"github.com/c9s/bbgo/pkg/types"
|
||||||
)
|
)
|
||||||
|
|
||||||
var trivialPrices = []byte(`[0]`)
|
var trivialPrices = []byte(`[0]`)
|
||||||
var trivialVolumes = []byte(`[1]`)
|
var trivialVolumes = []byte(`[1]`)
|
||||||
var easyPrices = []byte(`[1, 2, 3]`)
|
var easyPrices = []byte(`[1, 2, 3]`)
|
||||||
|
|
|
@ -1,4 +1,4 @@
|
||||||
// +build web
|
//go:build web
|
||||||
|
|
||||||
package server
|
package server
|
||||||
|
|
||||||
|
|
|
@ -1,4 +1,4 @@
|
||||||
// +build !web
|
//go:build !web
|
||||||
|
|
||||||
package server
|
package server
|
||||||
|
|
||||||
|
|
|
@ -670,7 +670,7 @@ func calculateBandPercentage(up, down, sma, midPrice float64) float64 {
|
||||||
return (midPrice - sma) / math.Abs(sma-down)
|
return (midPrice - sma) / math.Abs(sma-down)
|
||||||
} else if midPrice > sma {
|
} else if midPrice > sma {
|
||||||
// should be positive percentage
|
// should be positive percentage
|
||||||
return (midPrice - sma) / math.Abs(up - sma)
|
return (midPrice - sma) / math.Abs(up-sma)
|
||||||
}
|
}
|
||||||
|
|
||||||
return 0.0
|
return 0.0
|
||||||
|
|
|
@ -22,7 +22,6 @@ type Strategy struct {
|
||||||
|
|
||||||
Notifiability *bbgo.Notifiability
|
Notifiability *bbgo.Notifiability
|
||||||
|
|
||||||
|
|
||||||
TotalAmount fixedpoint.Value `json:"totalAmount,omitempty"`
|
TotalAmount fixedpoint.Value `json:"totalAmount,omitempty"`
|
||||||
|
|
||||||
// Interval is the period that you want to submit order
|
// Interval is the period that you want to submit order
|
||||||
|
|
|
@ -9,9 +9,9 @@ import (
|
||||||
log "github.com/sirupsen/logrus"
|
log "github.com/sirupsen/logrus"
|
||||||
|
|
||||||
"github.com/c9s/bbgo/pkg/bbgo"
|
"github.com/c9s/bbgo/pkg/bbgo"
|
||||||
|
"github.com/c9s/bbgo/pkg/fixedpoint"
|
||||||
"github.com/c9s/bbgo/pkg/indicator"
|
"github.com/c9s/bbgo/pkg/indicator"
|
||||||
"github.com/c9s/bbgo/pkg/types"
|
"github.com/c9s/bbgo/pkg/types"
|
||||||
"github.com/c9s/bbgo/pkg/fixedpoint"
|
|
||||||
)
|
)
|
||||||
|
|
||||||
const ID = "flashcrash"
|
const ID = "flashcrash"
|
||||||
|
|
|
@ -4,8 +4,8 @@ import (
|
||||||
"context"
|
"context"
|
||||||
|
|
||||||
"github.com/c9s/bbgo/pkg/bbgo"
|
"github.com/c9s/bbgo/pkg/bbgo"
|
||||||
"github.com/c9s/bbgo/pkg/types"
|
|
||||||
"github.com/c9s/bbgo/pkg/fixedpoint"
|
"github.com/c9s/bbgo/pkg/fixedpoint"
|
||||||
|
"github.com/c9s/bbgo/pkg/types"
|
||||||
)
|
)
|
||||||
|
|
||||||
const ID = "pricealert"
|
const ID = "pricealert"
|
||||||
|
@ -19,8 +19,8 @@ type Strategy struct {
|
||||||
bbgo.Notifiability
|
bbgo.Notifiability
|
||||||
|
|
||||||
// These fields will be filled from the config file (it translates YAML to JSON)
|
// These fields will be filled from the config file (it translates YAML to JSON)
|
||||||
Symbol string `json:"symbol"`
|
Symbol string `json:"symbol"`
|
||||||
Interval string `json:"interval"`
|
Interval string `json:"interval"`
|
||||||
MinChange fixedpoint.Value `json:"minChange"`
|
MinChange fixedpoint.Value `json:"minChange"`
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -6,11 +6,12 @@ import (
|
||||||
"github.com/sirupsen/logrus"
|
"github.com/sirupsen/logrus"
|
||||||
|
|
||||||
"github.com/c9s/bbgo/pkg/bbgo"
|
"github.com/c9s/bbgo/pkg/bbgo"
|
||||||
"github.com/c9s/bbgo/pkg/types"
|
|
||||||
"github.com/c9s/bbgo/pkg/fixedpoint"
|
"github.com/c9s/bbgo/pkg/fixedpoint"
|
||||||
|
"github.com/c9s/bbgo/pkg/types"
|
||||||
)
|
)
|
||||||
|
|
||||||
const ID = "skeleton"
|
const ID = "skeleton"
|
||||||
|
|
||||||
var log = logrus.WithField("strategy", ID)
|
var log = logrus.WithField("strategy", ID)
|
||||||
|
|
||||||
func init() {
|
func init() {
|
||||||
|
@ -25,7 +26,6 @@ func (s *Strategy) ID() string {
|
||||||
return ID
|
return ID
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
func (s *Strategy) Subscribe(session *bbgo.ExchangeSession) {
|
func (s *Strategy) Subscribe(session *bbgo.ExchangeSession) {
|
||||||
log.Infof("subscribe %s", s.Symbol)
|
log.Infof("subscribe %s", s.Symbol)
|
||||||
session.Subscribe(types.KLineChannel, s.Symbol, types.SubscribeOptions{Interval: "1m"})
|
session.Subscribe(types.KLineChannel, s.Symbol, types.SubscribeOptions{Interval: "1m"})
|
||||||
|
@ -35,7 +35,7 @@ var Ten = fixedpoint.NewFromInt(10)
|
||||||
|
|
||||||
// This strategy simply spent all available quote currency to buy the symbol whenever kline gets closed
|
// This strategy simply spent all available quote currency to buy the symbol whenever kline gets closed
|
||||||
func (s *Strategy) Run(ctx context.Context, orderExecutor bbgo.OrderExecutor, session *bbgo.ExchangeSession) error {
|
func (s *Strategy) Run(ctx context.Context, orderExecutor bbgo.OrderExecutor, session *bbgo.ExchangeSession) error {
|
||||||
market, ok := session.Market(s.Symbol)
|
market, ok := session.Market(s.Symbol)
|
||||||
if !ok {
|
if !ok {
|
||||||
log.Warnf("fetch market fail %s", s.Symbol)
|
log.Warnf("fetch market fail %s", s.Symbol)
|
||||||
return nil
|
return nil
|
||||||
|
@ -73,7 +73,7 @@ func (s *Strategy) Run(ctx context.Context, orderExecutor bbgo.OrderExecutor, se
|
||||||
log.Infof("connected")
|
log.Infof("connected")
|
||||||
})
|
})
|
||||||
|
|
||||||
session.MarketDataStream.OnKLineClosed(callback)
|
session.MarketDataStream.OnKLineClosed(callback)
|
||||||
|
|
||||||
return nil
|
return nil
|
||||||
}
|
}
|
||||||
|
|
|
@ -33,8 +33,8 @@ type State struct {
|
||||||
}
|
}
|
||||||
|
|
||||||
type Target struct {
|
type Target struct {
|
||||||
ProfitPercentage fixedpoint.Value `json:"profitPercentage"`
|
ProfitPercentage fixedpoint.Value `json:"profitPercentage"`
|
||||||
QuantityPercentage fixedpoint.Value `json:"quantityPercentage"`
|
QuantityPercentage fixedpoint.Value `json:"quantityPercentage"`
|
||||||
MarginOrderSideEffect types.MarginOrderSideEffectType `json:"marginOrderSideEffect"`
|
MarginOrderSideEffect types.MarginOrderSideEffectType `json:"marginOrderSideEffect"`
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -295,7 +295,7 @@ func (s *Strategy) calculateQuantity(session *bbgo.ExchangeSession, side types.S
|
||||||
baseBalance, _ := session.Account.Balance(s.Market.BaseCurrency)
|
baseBalance, _ := session.Account.Balance(s.Market.BaseCurrency)
|
||||||
if side == types.SideTypeSell {
|
if side == types.SideTypeSell {
|
||||||
// quantity = bbgo.AdjustQuantityByMaxAmount(quantity, closePrice, quota)
|
// quantity = bbgo.AdjustQuantityByMaxAmount(quantity, closePrice, quota)
|
||||||
if s.MinBaseAssetBalance.Sign() > 0 &&
|
if s.MinBaseAssetBalance.Sign() > 0 &&
|
||||||
baseBalance.Total().Sub(quantity).Compare(s.MinBaseAssetBalance) < 0 {
|
baseBalance.Total().Sub(quantity).Compare(s.MinBaseAssetBalance) < 0 {
|
||||||
quota := baseBalance.Available.Sub(s.MinBaseAssetBalance)
|
quota := baseBalance.Available.Sub(s.MinBaseAssetBalance)
|
||||||
quantity = bbgo.AdjustQuantityByMaxAmount(quantity, closePrice, quota)
|
quantity = bbgo.AdjustQuantityByMaxAmount(quantity, closePrice, quota)
|
||||||
|
|
|
@ -7,8 +7,8 @@ import (
|
||||||
log "github.com/sirupsen/logrus"
|
log "github.com/sirupsen/logrus"
|
||||||
|
|
||||||
"github.com/c9s/bbgo/pkg/bbgo"
|
"github.com/c9s/bbgo/pkg/bbgo"
|
||||||
"github.com/c9s/bbgo/pkg/types"
|
|
||||||
"github.com/c9s/bbgo/pkg/fixedpoint"
|
"github.com/c9s/bbgo/pkg/fixedpoint"
|
||||||
|
"github.com/c9s/bbgo/pkg/types"
|
||||||
)
|
)
|
||||||
|
|
||||||
const ID = "swing"
|
const ID = "swing"
|
||||||
|
|
|
@ -130,7 +130,6 @@ func (s *Strategy) listenToFundingRate(ctx context.Context, exchange *binance.Ex
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
previousIndex = index
|
previousIndex = index
|
||||||
if fundingRate24HoursLowIndex != nil {
|
if fundingRate24HoursLowIndex != nil {
|
||||||
if fundingRate24HoursLowIndex.Time.Before(time.Now().Add(24 * time.Hour)) {
|
if fundingRate24HoursLowIndex.Time.Before(time.Now().Add(24 * time.Hour)) {
|
||||||
|
|
|
@ -16,7 +16,7 @@ type State struct {
|
||||||
|
|
||||||
type ProfitStats struct {
|
type ProfitStats struct {
|
||||||
bbgo.ProfitStats
|
bbgo.ProfitStats
|
||||||
lock sync.Mutex
|
lock sync.Mutex
|
||||||
|
|
||||||
MakerExchange types.ExchangeName `json:"makerExchange"`
|
MakerExchange types.ExchangeName `json:"makerExchange"`
|
||||||
|
|
||||||
|
|
|
@ -232,7 +232,7 @@ func (s *Strategy) updateQuote(ctx context.Context, orderExecutionRouter bbgo.Or
|
||||||
// to make bid orders, we need enough base asset in the foreign exchange,
|
// to make bid orders, we need enough base asset in the foreign exchange,
|
||||||
// if the base asset balance is not enough for selling
|
// if the base asset balance is not enough for selling
|
||||||
if s.StopHedgeBaseBalance.Sign() > 0 {
|
if s.StopHedgeBaseBalance.Sign() > 0 {
|
||||||
minAvailable := s.StopHedgeBaseBalance.Add(s.sourceMarket.MinQuantity)
|
minAvailable := s.StopHedgeBaseBalance.Add(s.sourceMarket.MinQuantity)
|
||||||
if b.Available.Compare(minAvailable) > 0 {
|
if b.Available.Compare(minAvailable) > 0 {
|
||||||
hedgeQuota.BaseAsset.Add(b.Available.Sub(minAvailable))
|
hedgeQuota.BaseAsset.Add(b.Available.Sub(minAvailable))
|
||||||
} else {
|
} else {
|
||||||
|
@ -467,6 +467,7 @@ func (s *Strategy) updateQuote(ctx context.Context, orderExecutionRouter bbgo.Or
|
||||||
|
|
||||||
var lastPriceModifier = fixedpoint.NewFromFloat(1.001)
|
var lastPriceModifier = fixedpoint.NewFromFloat(1.001)
|
||||||
var minGap = fixedpoint.NewFromFloat(1.02)
|
var minGap = fixedpoint.NewFromFloat(1.02)
|
||||||
|
|
||||||
func (s *Strategy) Hedge(ctx context.Context, pos fixedpoint.Value) {
|
func (s *Strategy) Hedge(ctx context.Context, pos fixedpoint.Value) {
|
||||||
side := types.SideTypeBuy
|
side := types.SideTypeBuy
|
||||||
if pos.IsZero() {
|
if pos.IsZero() {
|
||||||
|
|
|
@ -1,2 +1 @@
|
||||||
package xnav
|
package xnav
|
||||||
|
|
||||||
|
|
|
@ -162,7 +162,7 @@ func (s *Strategy) generateOrders(symbol string, side types.SideType, price, pri
|
||||||
}
|
}
|
||||||
|
|
||||||
decdigits := priceTick.Abs().NumIntDigits()
|
decdigits := priceTick.Abs().NumIntDigits()
|
||||||
step := priceTick.Abs().MulExp(-decdigits+1)
|
step := priceTick.Abs().MulExp(-decdigits + 1)
|
||||||
|
|
||||||
for i := 0; i < numOrders; i++ {
|
for i := 0; i < numOrders; i++ {
|
||||||
quantityExp := fixedpoint.NewFromFloat(math.Exp(expBase.Float64()))
|
quantityExp := fixedpoint.NewFromFloat(math.Exp(expBase.Float64()))
|
||||||
|
@ -190,7 +190,7 @@ func (s *Strategy) generateOrders(symbol string, side types.SideType, price, pri
|
||||||
}
|
}
|
||||||
|
|
||||||
price = price.Add(priceTick)
|
price = price.Add(priceTick)
|
||||||
expBase = expBase.Add(step)
|
expBase = expBase.Add(step)
|
||||||
}
|
}
|
||||||
|
|
||||||
return orders
|
return orders
|
||||||
|
|
|
@ -1,2 +1 @@
|
||||||
package types
|
package types
|
||||||
|
|
||||||
|
|
|
@ -32,4 +32,3 @@ func IsFiatCurrency(currency string) bool {
|
||||||
}
|
}
|
||||||
return false
|
return false
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -1,8 +1,8 @@
|
||||||
package types
|
package types
|
||||||
|
|
||||||
import (
|
import (
|
||||||
"time"
|
|
||||||
"github.com/c9s/bbgo/pkg/fixedpoint"
|
"github.com/c9s/bbgo/pkg/fixedpoint"
|
||||||
|
"time"
|
||||||
)
|
)
|
||||||
|
|
||||||
type DepositStatus string
|
type DepositStatus string
|
||||||
|
@ -23,15 +23,15 @@ const (
|
||||||
)
|
)
|
||||||
|
|
||||||
type Deposit struct {
|
type Deposit struct {
|
||||||
GID int64 `json:"gid" db:"gid"`
|
GID int64 `json:"gid" db:"gid"`
|
||||||
Exchange ExchangeName `json:"exchange" db:"exchange"`
|
Exchange ExchangeName `json:"exchange" db:"exchange"`
|
||||||
Time Time `json:"time" db:"time"`
|
Time Time `json:"time" db:"time"`
|
||||||
Amount fixedpoint.Value `json:"amount" db:"amount"`
|
Amount fixedpoint.Value `json:"amount" db:"amount"`
|
||||||
Asset string `json:"asset" db:"asset"`
|
Asset string `json:"asset" db:"asset"`
|
||||||
Address string `json:"address" db:"address"`
|
Address string `json:"address" db:"address"`
|
||||||
AddressTag string `json:"addressTag"`
|
AddressTag string `json:"addressTag"`
|
||||||
TransactionID string `json:"transactionID" db:"txn_id"`
|
TransactionID string `json:"transactionID" db:"txn_id"`
|
||||||
Status DepositStatus `json:"status"`
|
Status DepositStatus `json:"status"`
|
||||||
}
|
}
|
||||||
|
|
||||||
func (d Deposit) EffectiveTime() time.Time {
|
func (d Deposit) EffectiveTime() time.Time {
|
||||||
|
|
|
@ -6,8 +6,8 @@ import (
|
||||||
|
|
||||||
"github.com/slack-go/slack"
|
"github.com/slack-go/slack"
|
||||||
|
|
||||||
"github.com/c9s/bbgo/pkg/util"
|
|
||||||
"github.com/c9s/bbgo/pkg/fixedpoint"
|
"github.com/c9s/bbgo/pkg/fixedpoint"
|
||||||
|
"github.com/c9s/bbgo/pkg/util"
|
||||||
)
|
)
|
||||||
|
|
||||||
type Direction int
|
type Direction int
|
||||||
|
@ -137,7 +137,6 @@ func (k KLine) GetAmplification() fixedpoint.Value {
|
||||||
return k.GetMaxChange().Div(k.GetLow())
|
return k.GetMaxChange().Div(k.GetLow())
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
// GetThickness returns the thickness of the kline. 1 => thick, 0.1 => thin
|
// GetThickness returns the thickness of the kline. 1 => thick, 0.1 => thin
|
||||||
func (k KLine) GetThickness() fixedpoint.Value {
|
func (k KLine) GetThickness() fixedpoint.Value {
|
||||||
out := k.GetChange().Div(k.GetMaxChange())
|
out := k.GetChange().Div(k.GetMaxChange())
|
||||||
|
@ -416,7 +415,7 @@ func (k KLineWindow) GetBody() fixedpoint.Value {
|
||||||
}
|
}
|
||||||
|
|
||||||
func (k KLineWindow) GetThickness() fixedpoint.Value {
|
func (k KLineWindow) GetThickness() fixedpoint.Value {
|
||||||
out := k.GetChange().Div(k.GetMaxChange())
|
out := k.GetChange().Div(k.GetMaxChange())
|
||||||
if out.Sign() < 0 {
|
if out.Sign() < 0 {
|
||||||
return out.Neg()
|
return out.Neg()
|
||||||
}
|
}
|
||||||
|
@ -471,7 +470,7 @@ func (k KLineWindow) SlackAttachment() slack.Attachment {
|
||||||
return slack.Attachment{
|
return slack.Attachment{
|
||||||
Text: fmt.Sprintf("*%s* KLineWindow %s x %d", first.Symbol, first.Interval, windowSize),
|
Text: fmt.Sprintf("*%s* KLineWindow %s x %d", first.Symbol, first.Interval, windowSize),
|
||||||
Color: k.Color(),
|
Color: k.Color(),
|
||||||
Fields: []slack.AttachmentField {
|
Fields: []slack.AttachmentField{
|
||||||
{Title: "Open", Value: util.FormatValue(k.GetOpen(), 2), Short: true},
|
{Title: "Open", Value: util.FormatValue(k.GetOpen(), 2), Short: true},
|
||||||
{Title: "High", Value: util.FormatValue(k.GetHigh(), 2), Short: true},
|
{Title: "High", Value: util.FormatValue(k.GetHigh(), 2), Short: true},
|
||||||
{Title: "Low", Value: util.FormatValue(k.GetLow(), 2), Short: true},
|
{Title: "Low", Value: util.FormatValue(k.GetLow(), 2), Short: true},
|
||||||
|
|
|
@ -1,9 +1,9 @@
|
||||||
package types
|
package types
|
||||||
|
|
||||||
import (
|
import (
|
||||||
"testing"
|
|
||||||
"github.com/stretchr/testify/assert"
|
|
||||||
"encoding/json"
|
"encoding/json"
|
||||||
|
"github.com/stretchr/testify/assert"
|
||||||
|
"testing"
|
||||||
)
|
)
|
||||||
|
|
||||||
func TestKLineWindow_Tail(t *testing.T) {
|
func TestKLineWindow_Tail(t *testing.T) {
|
||||||
|
@ -34,7 +34,7 @@ func TestKLineWindow_Tail(t *testing.T) {
|
||||||
}
|
}
|
||||||
|
|
||||||
func TestKLineWindow_Truncate(t *testing.T) {
|
func TestKLineWindow_Truncate(t *testing.T) {
|
||||||
var jsonWin = []byte(`[
|
var jsonWin = []byte(`[
|
||||||
{"open": 11600.0, "close": 11600.0, "high": 11600.0, "low": 11600.0},
|
{"open": 11600.0, "close": 11600.0, "high": 11600.0, "low": 11600.0},
|
||||||
{"open": 11601.0, "close": 11600.0, "high": 11600.0, "low": 11600.0},
|
{"open": 11601.0, "close": 11600.0, "high": 11600.0, "low": 11600.0},
|
||||||
{"open": 11602.0, "close": 11600.0, "high": 11600.0, "low": 11600.0},
|
{"open": 11602.0, "close": 11600.0, "high": 11600.0, "low": 11600.0},
|
||||||
|
|
|
@ -5,11 +5,11 @@ import (
|
||||||
"testing"
|
"testing"
|
||||||
"time"
|
"time"
|
||||||
|
|
||||||
"github.com/stretchr/testify/assert"
|
|
||||||
"github.com/c9s/bbgo/pkg/fixedpoint"
|
"github.com/c9s/bbgo/pkg/fixedpoint"
|
||||||
|
"github.com/stretchr/testify/assert"
|
||||||
)
|
)
|
||||||
|
|
||||||
var s func(string)fixedpoint.Value = fixedpoint.MustNewFromString
|
var s func(string) fixedpoint.Value = fixedpoint.MustNewFromString
|
||||||
|
|
||||||
func TestFormatQuantity(t *testing.T) {
|
func TestFormatQuantity(t *testing.T) {
|
||||||
quantity := formatQuantity(
|
quantity := formatQuantity(
|
||||||
|
@ -53,7 +53,7 @@ func TestDurationParse(t *testing.T) {
|
||||||
{
|
{
|
||||||
name: "float64 to second",
|
name: "float64 to second",
|
||||||
input: `{ "duration": 1.1 }`,
|
input: `{ "duration": 1.1 }`,
|
||||||
expected: Duration(time.Second + 100 * time.Millisecond),
|
expected: Duration(time.Second + 100*time.Millisecond),
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
name: "2m",
|
name: "2m",
|
||||||
|
@ -63,7 +63,7 @@ func TestDurationParse(t *testing.T) {
|
||||||
{
|
{
|
||||||
name: "2m3s",
|
name: "2m3s",
|
||||||
input: `{ "duration": "2m3s" }`,
|
input: `{ "duration": "2m3s" }`,
|
||||||
expected: Duration(2 * time.Minute + 3 * time.Second),
|
expected: Duration(2*time.Minute + 3*time.Second),
|
||||||
},
|
},
|
||||||
}
|
}
|
||||||
for _, test := range tests {
|
for _, test := range tests {
|
||||||
|
|
|
@ -10,8 +10,8 @@ import (
|
||||||
"github.com/pkg/errors"
|
"github.com/pkg/errors"
|
||||||
"github.com/slack-go/slack"
|
"github.com/slack-go/slack"
|
||||||
|
|
||||||
"github.com/c9s/bbgo/pkg/util"
|
|
||||||
"github.com/c9s/bbgo/pkg/fixedpoint"
|
"github.com/c9s/bbgo/pkg/fixedpoint"
|
||||||
|
"github.com/c9s/bbgo/pkg/util"
|
||||||
)
|
)
|
||||||
|
|
||||||
func init() {
|
func init() {
|
||||||
|
@ -186,8 +186,8 @@ func (o SubmitOrder) SlackAttachment() slack.Attachment {
|
||||||
}
|
}
|
||||||
|
|
||||||
type OrderQuery struct {
|
type OrderQuery struct {
|
||||||
Symbol string
|
Symbol string
|
||||||
OrderID string
|
OrderID string
|
||||||
ClientOrderID string
|
ClientOrderID string
|
||||||
}
|
}
|
||||||
|
|
||||||
|
@ -201,11 +201,11 @@ type Order struct {
|
||||||
OrderID uint64 `json:"orderID" db:"order_id"` // order id
|
OrderID uint64 `json:"orderID" db:"order_id"` // order id
|
||||||
UUID string `json:"uuid,omitempty"`
|
UUID string `json:"uuid,omitempty"`
|
||||||
|
|
||||||
Status OrderStatus `json:"status" db:"status"`
|
Status OrderStatus `json:"status" db:"status"`
|
||||||
ExecutedQuantity fixedpoint.Value `json:"executedQuantity" db:"executed_quantity"`
|
ExecutedQuantity fixedpoint.Value `json:"executedQuantity" db:"executed_quantity"`
|
||||||
IsWorking bool `json:"isWorking" db:"is_working"`
|
IsWorking bool `json:"isWorking" db:"is_working"`
|
||||||
CreationTime Time `json:"creationTime" db:"created_at"`
|
CreationTime Time `json:"creationTime" db:"created_at"`
|
||||||
UpdateTime Time `json:"updateTime" db:"updated_at"`
|
UpdateTime Time `json:"updateTime" db:"updated_at"`
|
||||||
|
|
||||||
IsMargin bool `json:"isMargin" db:"is_margin"`
|
IsMargin bool `json:"isMargin" db:"is_margin"`
|
||||||
IsIsolated bool `json:"isIsolated" db:"is_isolated"`
|
IsIsolated bool `json:"isIsolated" db:"is_isolated"`
|
||||||
|
|
|
@ -129,10 +129,10 @@ func TestPosition(t *testing.T) {
|
||||||
},
|
},
|
||||||
expectedAverageCost: fixedpoint.NewFromFloat(1000.0 * 0.01).
|
expectedAverageCost: fixedpoint.NewFromFloat(1000.0 * 0.01).
|
||||||
Div(fixedpoint.NewFromFloat(0.01).Mul(fixedpoint.One.Sub(feeRateValue))),
|
Div(fixedpoint.NewFromFloat(0.01).Mul(fixedpoint.One.Sub(feeRateValue))),
|
||||||
expectedBase: fixedpoint.NewFromFloat(0.01).
|
expectedBase: fixedpoint.NewFromFloat(0.01).
|
||||||
Sub(fixedpoint.NewFromFloat(0.01).Mul(feeRateValue)),
|
Sub(fixedpoint.NewFromFloat(0.01).Mul(feeRateValue)),
|
||||||
expectedQuote: fixedpoint.NewFromFloat(0 - 1000.0*0.01),
|
expectedQuote: fixedpoint.NewFromFloat(0 - 1000.0*0.01),
|
||||||
expectedProfit: fixedpoint.Zero,
|
expectedProfit: fixedpoint.Zero,
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
name: "quote fee",
|
name: "quote fee",
|
||||||
|
@ -149,9 +149,9 @@ func TestPosition(t *testing.T) {
|
||||||
expectedAverageCost: fixedpoint.NewFromFloat(1000.0 * 0.01).
|
expectedAverageCost: fixedpoint.NewFromFloat(1000.0 * 0.01).
|
||||||
Mul(fixedpoint.One.Sub(feeRateValue)).
|
Mul(fixedpoint.One.Sub(feeRateValue)).
|
||||||
Div(fixedpoint.NewFromFloat(0.01)),
|
Div(fixedpoint.NewFromFloat(0.01)),
|
||||||
expectedBase: fixedpoint.NewFromFloat(-0.01),
|
expectedBase: fixedpoint.NewFromFloat(-0.01),
|
||||||
expectedQuote: fixedpoint.NewFromFloat(0.0 + 1000.0 * 0.01 * (1.0 - feeRate)),
|
expectedQuote: fixedpoint.NewFromFloat(0.0 + 1000.0*0.01*(1.0-feeRate)),
|
||||||
expectedProfit: fixedpoint.Zero,
|
expectedProfit: fixedpoint.Zero,
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
name: "long",
|
name: "long",
|
||||||
|
|
|
@ -3,8 +3,8 @@ package types
|
||||||
import (
|
import (
|
||||||
"testing"
|
"testing"
|
||||||
|
|
||||||
"github.com/stretchr/testify/assert"
|
|
||||||
"github.com/c9s/bbgo/pkg/fixedpoint"
|
"github.com/c9s/bbgo/pkg/fixedpoint"
|
||||||
|
"github.com/stretchr/testify/assert"
|
||||||
)
|
)
|
||||||
|
|
||||||
func TestPriceVolumeSlice_Remove(t *testing.T) {
|
func TestPriceVolumeSlice_Remove(t *testing.T) {
|
||||||
|
|
|
@ -9,7 +9,7 @@ import (
|
||||||
"github.com/c9s/bbgo/pkg/fixedpoint"
|
"github.com/c9s/bbgo/pkg/fixedpoint"
|
||||||
)
|
)
|
||||||
|
|
||||||
var itov func(int64)fixedpoint.Value = fixedpoint.NewFromInt
|
var itov func(int64) fixedpoint.Value = fixedpoint.NewFromInt
|
||||||
|
|
||||||
func TestRBTree_InsertAndDelete(t *testing.T) {
|
func TestRBTree_InsertAndDelete(t *testing.T) {
|
||||||
tree := NewRBTree()
|
tree := NewRBTree()
|
||||||
|
|
|
@ -33,10 +33,12 @@ type Reward struct {
|
||||||
}
|
}
|
||||||
|
|
||||||
type RewardSlice []Reward
|
type RewardSlice []Reward
|
||||||
|
|
||||||
func (s RewardSlice) Len() int { return len(s) }
|
func (s RewardSlice) Len() int { return len(s) }
|
||||||
func (s RewardSlice) Swap(i, j int) { s[i], s[j] = s[j], s[i] }
|
func (s RewardSlice) Swap(i, j int) { s[i], s[j] = s[j], s[i] }
|
||||||
|
|
||||||
type RewardSliceByCreationTime RewardSlice
|
type RewardSliceByCreationTime RewardSlice
|
||||||
|
|
||||||
func (s RewardSliceByCreationTime) Len() int { return len(s) }
|
func (s RewardSliceByCreationTime) Len() int { return len(s) }
|
||||||
func (s RewardSliceByCreationTime) Swap(i, j int) { s[i], s[j] = s[j], s[i] }
|
func (s RewardSliceByCreationTime) Swap(i, j int) { s[i], s[j] = s[j], s[i] }
|
||||||
|
|
||||||
|
|
|
@ -1,8 +1,8 @@
|
||||||
package types
|
package types
|
||||||
|
|
||||||
import (
|
import (
|
||||||
"time"
|
|
||||||
"github.com/c9s/bbgo/pkg/fixedpoint"
|
"github.com/c9s/bbgo/pkg/fixedpoint"
|
||||||
|
"time"
|
||||||
)
|
)
|
||||||
|
|
||||||
type Ticker struct {
|
type Ticker struct {
|
||||||
|
|
|
@ -52,20 +52,20 @@ type Trade struct {
|
||||||
GID int64 `json:"gid" db:"gid"`
|
GID int64 `json:"gid" db:"gid"`
|
||||||
|
|
||||||
// ID is the source trade ID
|
// ID is the source trade ID
|
||||||
ID uint64 `json:"id" db:"id"`
|
ID uint64 `json:"id" db:"id"`
|
||||||
OrderID uint64 `json:"orderID" db:"order_id"`
|
OrderID uint64 `json:"orderID" db:"order_id"`
|
||||||
Exchange ExchangeName `json:"exchange" db:"exchange"`
|
Exchange ExchangeName `json:"exchange" db:"exchange"`
|
||||||
Price fixedpoint.Value `json:"price" db:"price"`
|
Price fixedpoint.Value `json:"price" db:"price"`
|
||||||
Quantity fixedpoint.Value `json:"quantity" db:"quantity"`
|
Quantity fixedpoint.Value `json:"quantity" db:"quantity"`
|
||||||
QuoteQuantity fixedpoint.Value `json:"quoteQuantity" db:"quote_quantity"`
|
QuoteQuantity fixedpoint.Value `json:"quoteQuantity" db:"quote_quantity"`
|
||||||
Symbol string `json:"symbol" db:"symbol"`
|
Symbol string `json:"symbol" db:"symbol"`
|
||||||
|
|
||||||
Side SideType `json:"side" db:"side"`
|
Side SideType `json:"side" db:"side"`
|
||||||
IsBuyer bool `json:"isBuyer" db:"is_buyer"`
|
IsBuyer bool `json:"isBuyer" db:"is_buyer"`
|
||||||
IsMaker bool `json:"isMaker" db:"is_maker"`
|
IsMaker bool `json:"isMaker" db:"is_maker"`
|
||||||
Time Time `json:"tradedAt" db:"traded_at"`
|
Time Time `json:"tradedAt" db:"traded_at"`
|
||||||
Fee fixedpoint.Value `json:"fee" db:"fee"`
|
Fee fixedpoint.Value `json:"fee" db:"fee"`
|
||||||
FeeCurrency string `json:"feeCurrency" db:"fee_currency"`
|
FeeCurrency string `json:"feeCurrency" db:"fee_currency"`
|
||||||
|
|
||||||
IsMargin bool `json:"isMargin" db:"is_margin"`
|
IsMargin bool `json:"isMargin" db:"is_margin"`
|
||||||
IsFutures bool `json:"isFutures" db:"is_futures"`
|
IsFutures bool `json:"isFutures" db:"is_futures"`
|
||||||
|
@ -146,7 +146,6 @@ func (trade Trade) PlainText() string {
|
||||||
|
|
||||||
var slackTradeTextTemplate = ":handshake: Trade {{ .Symbol }} {{ .Side }} {{ .Quantity }} @ {{ .Price }}"
|
var slackTradeTextTemplate = ":handshake: Trade {{ .Symbol }} {{ .Side }} {{ .Quantity }} @ {{ .Price }}"
|
||||||
|
|
||||||
|
|
||||||
func exchangeFooterIcon(exName ExchangeName) string {
|
func exchangeFooterIcon(exName ExchangeName) string {
|
||||||
footerIcon := ""
|
footerIcon := ""
|
||||||
|
|
||||||
|
|
|
@ -29,9 +29,9 @@ func Test_trimTrailingZero(t *testing.T) {
|
||||||
{
|
{
|
||||||
name: "non trailing zero",
|
name: "non trailing zero",
|
||||||
args: args{
|
args: args{
|
||||||
a: "1.0001234567",
|
a: "1.00012345",
|
||||||
},
|
},
|
||||||
want: "1.0001234567",
|
want: "1.00012345",
|
||||||
},
|
},
|
||||||
{
|
{
|
||||||
name: "integer",
|
name: "integer",
|
||||||
|
|
|
@ -2,25 +2,25 @@ package types
|
||||||
|
|
||||||
import (
|
import (
|
||||||
"fmt"
|
"fmt"
|
||||||
"time"
|
|
||||||
"github.com/c9s/bbgo/pkg/fixedpoint"
|
"github.com/c9s/bbgo/pkg/fixedpoint"
|
||||||
|
"time"
|
||||||
)
|
)
|
||||||
|
|
||||||
type Withdraw struct {
|
type Withdraw struct {
|
||||||
GID int64 `json:"gid" db:"gid"`
|
GID int64 `json:"gid" db:"gid"`
|
||||||
Exchange ExchangeName `json:"exchange" db:"exchange"`
|
Exchange ExchangeName `json:"exchange" db:"exchange"`
|
||||||
Asset string `json:"asset" db:"asset"`
|
Asset string `json:"asset" db:"asset"`
|
||||||
Amount fixedpoint.Value `json:"amount" db:"amount"`
|
Amount fixedpoint.Value `json:"amount" db:"amount"`
|
||||||
Address string `json:"address" db:"address"`
|
Address string `json:"address" db:"address"`
|
||||||
AddressTag string `json:"addressTag"`
|
AddressTag string `json:"addressTag"`
|
||||||
Status string `json:"status"`
|
Status string `json:"status"`
|
||||||
|
|
||||||
TransactionID string `json:"transactionID" db:"txn_id"`
|
TransactionID string `json:"transactionID" db:"txn_id"`
|
||||||
TransactionFee fixedpoint.Value `json:"transactionFee" db:"txn_fee"`
|
TransactionFee fixedpoint.Value `json:"transactionFee" db:"txn_fee"`
|
||||||
TransactionFeeCurrency string `json:"transactionFeeCurrency" db:"txn_fee_currency"`
|
TransactionFeeCurrency string `json:"transactionFeeCurrency" db:"txn_fee_currency"`
|
||||||
WithdrawOrderID string `json:"withdrawOrderId"`
|
WithdrawOrderID string `json:"withdrawOrderId"`
|
||||||
ApplyTime Time `json:"applyTime" db:"time"`
|
ApplyTime Time `json:"applyTime" db:"time"`
|
||||||
Network string `json:"network" db:"network"`
|
Network string `json:"network" db:"network"`
|
||||||
}
|
}
|
||||||
|
|
||||||
func (w Withdraw) String() string {
|
func (w Withdraw) String() string {
|
||||||
|
@ -35,4 +35,3 @@ type WithdrawalOptions struct {
|
||||||
Network string
|
Network string
|
||||||
AddressTag string
|
AddressTag string
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -1,9 +1,9 @@
|
||||||
package util
|
package util
|
||||||
|
|
||||||
import (
|
import (
|
||||||
|
"github.com/c9s/bbgo/pkg/fixedpoint"
|
||||||
"math"
|
"math"
|
||||||
"strconv"
|
"strconv"
|
||||||
"github.com/c9s/bbgo/pkg/fixedpoint"
|
|
||||||
)
|
)
|
||||||
|
|
||||||
const MaxDigits = 18 // MAX_INT64 ~ 9 * 10^18
|
const MaxDigits = 18 // MAX_INT64 ~ 9 * 10^18
|
||||||
|
|
|
@ -11,9 +11,9 @@ func TestReonce_DoAndReset(t *testing.T) {
|
||||||
var cnt = 0
|
var cnt = 0
|
||||||
var reonce Reonce
|
var reonce Reonce
|
||||||
go reonce.Do(func() {
|
go reonce.Do(func() {
|
||||||
t.Log("once #1")
|
t.Log("once #1")
|
||||||
time.Sleep(10 * time.Millisecond)
|
time.Sleep(10 * time.Millisecond)
|
||||||
cnt++
|
cnt++
|
||||||
})
|
})
|
||||||
|
|
||||||
// make sure it's locked
|
// make sure it's locked
|
||||||
|
@ -22,12 +22,11 @@ func TestReonce_DoAndReset(t *testing.T) {
|
||||||
reonce.Reset()
|
reonce.Reset()
|
||||||
|
|
||||||
go reonce.Do(func() {
|
go reonce.Do(func() {
|
||||||
t.Log("once #2")
|
t.Log("once #2")
|
||||||
time.Sleep(10 * time.Millisecond)
|
time.Sleep(10 * time.Millisecond)
|
||||||
cnt++
|
cnt++
|
||||||
})
|
})
|
||||||
|
|
||||||
time.Sleep(time.Second)
|
time.Sleep(time.Second)
|
||||||
assert.Equal(t, 2, cnt)
|
assert.Equal(t, 2, cnt)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
|
@ -17,7 +17,7 @@ func BeginningOfTheDay(t time.Time) time.Time {
|
||||||
}
|
}
|
||||||
|
|
||||||
func Over24Hours(since time.Time) bool {
|
func Over24Hours(since time.Time) bool {
|
||||||
return time.Since(since) >= 24 * time.Hour
|
return time.Since(since) >= 24*time.Hour
|
||||||
}
|
}
|
||||||
|
|
||||||
func UnixMilli() int64 {
|
func UnixMilli() int64 {
|
||||||
|
@ -33,7 +33,3 @@ func ParseTimeWithFormats(strTime string, formats []string) (time.Time, error) {
|
||||||
}
|
}
|
||||||
return time.Time{}, fmt.Errorf("failed to parse time %s, valid formats are %+v", strTime, formats)
|
return time.Time{}, fmt.Errorf("failed to parse time %s, valid formats are %+v", strTime, formats)
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
||||||
|
|
Loading…
Reference in New Issue
Block a user