Migrate from gometalinter.v2 to golangci-lint (#249)

* Migrate from gometalinter.v2 to golangci-lint
This commit is contained in:
Adrian Gallagher
2019-03-01 16:10:29 +11:00
committed by GitHub
parent 81852f2e01
commit 7dcb1ab553
133 changed files with 2179 additions and 2204 deletions

View File

@@ -67,11 +67,11 @@ func (a *Alphapoint) SetDefaults() {
// GetTicker returns current ticker information from Alphapoint for a selected
// currency pair ie "BTCUSD"
func (a *Alphapoint) GetTicker(currencyPair string) (Ticker, error) {
request := make(map[string]interface{})
request["productPair"] = currencyPair
req := make(map[string]interface{})
req["productPair"] = currencyPair
response := Ticker{}
err := a.SendHTTPRequest(http.MethodPost, alphapointTicker, request, &response)
err := a.SendHTTPRequest(http.MethodPost, alphapointTicker, req, &response)
if err != nil {
return response, err
}
@@ -88,13 +88,13 @@ func (a *Alphapoint) GetTicker(currencyPair string) (Ticker, error) {
// 0 (default: 0)
// Count: specifies the number of trades to return (default: 10)
func (a *Alphapoint) GetTrades(currencyPair string, startIndex, count int) (Trades, error) {
request := make(map[string]interface{})
request["ins"] = currencyPair
request["startIndex"] = startIndex
request["Count"] = count
req := make(map[string]interface{})
req["ins"] = currencyPair
req["startIndex"] = startIndex
req["Count"] = count
response := Trades{}
err := a.SendHTTPRequest(http.MethodPost, alphapointTrades, request, &response)
err := a.SendHTTPRequest(http.MethodPost, alphapointTrades, req, &response)
if err != nil {
return response, err
}
@@ -109,13 +109,13 @@ func (a *Alphapoint) GetTrades(currencyPair string, startIndex, count int) (Trad
// StartDate - specifies the starting time in epoch time, type is long
// EndDate - specifies the end time in epoch time, type is long
func (a *Alphapoint) GetTradesByDate(currencyPair string, startDate, endDate int64) (Trades, error) {
request := make(map[string]interface{})
request["ins"] = currencyPair
request["startDate"] = startDate
request["endDate"] = endDate
req := make(map[string]interface{})
req["ins"] = currencyPair
req["startDate"] = startDate
req["endDate"] = endDate
response := Trades{}
err := a.SendHTTPRequest(http.MethodPost, alphapointTradesByDate, request, &response)
err := a.SendHTTPRequest(http.MethodPost, alphapointTradesByDate, req, &response)
if err != nil {
return response, err
}
@@ -128,11 +128,11 @@ func (a *Alphapoint) GetTradesByDate(currencyPair string, startDate, endDate int
// GetOrderbook fetches the current orderbook for a given currency pair
// CurrencyPair - trade pair (ex: “BTCUSD”)
func (a *Alphapoint) GetOrderbook(currencyPair string) (Orderbook, error) {
request := make(map[string]interface{})
request["productPair"] = currencyPair
req := make(map[string]interface{})
req["productPair"] = currencyPair
response := Orderbook{}
err := a.SendHTTPRequest(http.MethodPost, alphapointOrderbook, request, &response)
err := a.SendHTTPRequest(http.MethodPost, alphapointOrderbook, req, &response)
if err != nil {
return response, err
}
@@ -183,17 +183,17 @@ func (a *Alphapoint) CreateAccount(firstName, lastName, email, phone, password s
)
}
request := make(map[string]interface{})
request["firstname"] = firstName
request["lastname"] = lastName
request["email"] = email
request["phone"] = phone
request["password"] = password
req := make(map[string]interface{})
req["firstname"] = firstName
req["lastname"] = lastName
req["email"] = email
req["phone"] = phone
req["password"] = password
response := Response{}
err := a.SendAuthenticatedHTTPRequest(http.MethodPost, alphapointCreateAccount, request, &response)
err := a.SendAuthenticatedHTTPRequest(http.MethodPost, alphapointCreateAccount, req, &response)
if err != nil {
return fmt.Errorf("Alphapoint Error - CreateAccount HTTPRequest - reason: %s", err)
return fmt.Errorf("unable to create account. Reason: %s", err)
}
if !response.IsAccepted {
return errors.New(response.RejectReason)
@@ -254,13 +254,13 @@ func (a *Alphapoint) SetUserInfo(firstName, lastName, cell2FACountryCode, cell2F
},
}
request := make(map[string]interface{})
request["userInfoKVP"] = userInfoKVPs
req := make(map[string]interface{})
req["userInfoKVP"] = userInfoKVPs
err := a.SendAuthenticatedHTTPRequest(
http.MethodPost,
alphapointUserInfo,
request,
req,
&response,
)
if err != nil {
@@ -296,16 +296,16 @@ func (a *Alphapoint) GetAccountInformation() (AccountInfo, error) {
// StartIndex - Starting index, if less than 0 then start from the beginning
// Count - Returns last trade, (Default: 30)
func (a *Alphapoint) GetAccountTrades(currencyPair string, startIndex, count int) (Trades, error) {
request := make(map[string]interface{})
request["ins"] = currencyPair
request["startIndex"] = startIndex
request["count"] = count
req := make(map[string]interface{})
req["ins"] = currencyPair
req["startIndex"] = startIndex
req["count"] = count
response := Trades{}
err := a.SendAuthenticatedHTTPRequest(
http.MethodPost,
alphapointAccountTrades,
request,
req,
&response,
)
if err != nil {
@@ -339,17 +339,17 @@ func (a *Alphapoint) GetDepositAddresses() ([]DepositAddresses, error) {
// amount - Amount (ex: “.011”)
// address - Withdraw address
func (a *Alphapoint) WithdrawCoins(symbol, product, address string, amount float64) error {
request := make(map[string]interface{})
request["ins"] = symbol
request["product"] = product
request["amount"] = strconv.FormatFloat(amount, 'f', -1, 64)
request["sendToAddress"] = address
req := make(map[string]interface{})
req["ins"] = symbol
req["product"] = product
req["amount"] = strconv.FormatFloat(amount, 'f', -1, 64)
req["sendToAddress"] = address
response := Response{}
err := a.SendAuthenticatedHTTPRequest(
http.MethodPost,
alphapointWithdraw,
request,
req,
&response,
)
if err != nil {
@@ -377,18 +377,18 @@ func (a *Alphapoint) convertOrderTypeToOrderTypeNumber(orderType string) (orderT
// price - Price in USD
func (a *Alphapoint) CreateOrder(symbol, side, orderType string, quantity, price float64) (int64, error) {
orderTypeNumber := a.convertOrderTypeToOrderTypeNumber(orderType)
request := make(map[string]interface{})
request["ins"] = symbol
request["side"] = side
request["orderType"] = orderTypeNumber
request["qty"] = strconv.FormatFloat(quantity, 'f', -1, 64)
request["px"] = strconv.FormatFloat(price, 'f', -1, 64)
req := make(map[string]interface{})
req["ins"] = symbol
req["side"] = side
req["orderType"] = orderTypeNumber
req["qty"] = strconv.FormatFloat(quantity, 'f', -1, 64)
req["px"] = strconv.FormatFloat(price, 'f', -1, 64)
response := Response{}
err := a.SendAuthenticatedHTTPRequest(
http.MethodPost,
alphapointCreateOrder,
request,
req,
&response,
)
if err != nil {
@@ -408,17 +408,17 @@ func (a *Alphapoint) CreateOrder(symbol, side, orderType string, quantity, price
// book. A buy order will be modified to the highest bid and a sell order will
// be modified to the lowest ask price. “1” means "Execute now", which will
// convert a limit order into a market order.
func (a *Alphapoint) ModifyExistingOrder(symbol string, OrderID, action int64) (int64, error) {
request := make(map[string]interface{})
request["ins"] = symbol
request["serverOrderId"] = OrderID
request["modifyAction"] = action
func (a *Alphapoint) ModifyExistingOrder(symbol string, orderID, action int64) (int64, error) {
req := make(map[string]interface{})
req["ins"] = symbol
req["serverOrderId"] = orderID
req["modifyAction"] = action
response := Response{}
err := a.SendAuthenticatedHTTPRequest(
http.MethodPost,
alphapointModifyOrder,
request,
req,
&response,
)
if err != nil {
@@ -433,16 +433,16 @@ func (a *Alphapoint) ModifyExistingOrder(symbol string, OrderID, action int64) (
// CancelExistingOrder cancels an order that has not been executed.
// symbol - Instrument code (ex: “BTCUSD”)
// OrderId - Order id (ex: 1000)
func (a *Alphapoint) CancelExistingOrder(OrderID int64, OMSID string) (int64, error) {
request := make(map[string]interface{})
request["OrderId"] = OrderID
request["OMSId"] = OMSID
func (a *Alphapoint) CancelExistingOrder(orderID int64, omsid string) (int64, error) {
req := make(map[string]interface{})
req["OrderId"] = orderID
req["OMSId"] = omsid
response := Response{}
err := a.SendAuthenticatedHTTPRequest(
http.MethodPost,
alphapointCancelOrder,
request,
req,
&response,
)
if err != nil {
@@ -456,15 +456,15 @@ func (a *Alphapoint) CancelExistingOrder(OrderID int64, OMSID string) (int64, er
// CancelAllExistingOrders cancels all open orders by symbol
// symbol - Instrument code (ex: “BTCUSD”)
func (a *Alphapoint) CancelAllExistingOrders(OMSID string) error {
request := make(map[string]interface{})
request["OMSId"] = OMSID
func (a *Alphapoint) CancelAllExistingOrders(omsid string) error {
req := make(map[string]interface{})
req["OMSId"] = omsid
response := Response{}
err := a.SendAuthenticatedHTTPRequest(
http.MethodPost,
alphapointCancelAllOrders,
request,
req,
&response,
)
if err != nil {
@@ -501,17 +501,17 @@ func (a *Alphapoint) GetOrders() ([]OpenOrders, error) {
// quantity - Quantity
// price - Price in USD
func (a *Alphapoint) GetOrderFee(symbol, side string, quantity, price float64) (float64, error) {
request := make(map[string]interface{})
request["ins"] = symbol
request["side"] = side
request["qty"] = strconv.FormatFloat(quantity, 'f', -1, 64)
request["px"] = strconv.FormatFloat(price, 'f', -1, 64)
req := make(map[string]interface{})
req["ins"] = symbol
req["side"] = side
req["qty"] = strconv.FormatFloat(quantity, 'f', -1, 64)
req["px"] = strconv.FormatFloat(price, 'f', -1, 64)
response := Response{}
err := a.SendAuthenticatedHTTPRequest(
http.MethodPost,
alphapointOrderFee,
request,
req,
&response,
)
if err != nil {
@@ -531,7 +531,7 @@ func (a *Alphapoint) SendHTTPRequest(method, path string, data map[string]interf
PayloadJSON, err := common.JSONEncode(data)
if err != nil {
return errors.New("SendHTTPRequest: Unable to JSON request")
return errors.New("unable to JSON request")
}
return a.SendPayload(method, path, headers, bytes.NewBuffer(PayloadJSON), result, false, a.Verbose)
@@ -559,7 +559,7 @@ func (a *Alphapoint) SendAuthenticatedHTTPRequest(method, path string, data map[
PayloadJSON, err := common.JSONEncode(data)
if err != nil {
return errors.New("SendAuthenticatedHTTPRequest: Unable to JSON request")
return errors.New("unable to JSON request")
}
return a.SendPayload(method, path, headers, bytes.NewBuffer(PayloadJSON), result, true, a.Verbose)

View File

@@ -42,8 +42,7 @@ func (a *Alphapoint) WebsocketClient() {
break
}
switch msgType {
case websocket.TextMessage:
if msgType == websocket.TextMessage {
type MsgType struct {
MessageType string `json:"messageType"`
}
@@ -55,8 +54,7 @@ func (a *Alphapoint) WebsocketClient() {
continue
}
switch msgType.MessageType {
case "Ticker":
if msgType.MessageType == "Ticker" {
ticker := WebsocketTicker{}
err = common.JSONDecode(resp, &ticker)
if err != nil {

View File

@@ -8,7 +8,7 @@ import (
"github.com/thrasher-/gocryptotrader/common"
"github.com/thrasher-/gocryptotrader/currency/pair"
"github.com/thrasher-/gocryptotrader/exchanges"
exchange "github.com/thrasher-/gocryptotrader/exchanges"
"github.com/thrasher-/gocryptotrader/exchanges/orderbook"
"github.com/thrasher-/gocryptotrader/exchanges/ticker"
)
@@ -133,7 +133,7 @@ func (a *Alphapoint) SubmitOrder(p pair.CurrencyPair, side exchange.OrderSide, o
// ModifyOrder will allow of changing orderbook placement and limit to
// market conversion
func (a *Alphapoint) ModifyOrder(action exchange.ModifyOrder) (string, error) {
func (a *Alphapoint) ModifyOrder(_ exchange.ModifyOrder) (string, error) {
return "", common.ErrNotYetImplemented
}

View File

@@ -75,7 +75,7 @@ func (a *ANX) SetDefaults() {
a.WebsocketInit()
}
//Setup is run on startup to setup exchange with config values
// Setup is run on startup to setup exchange with config values
func (a *ANX) Setup(exch config.ExchangeConfig) {
if !exch.Enabled {
a.SetEnabled(false)
@@ -129,32 +129,30 @@ func (a *ANX) GetCurrencies() (CurrenciesStore, error) {
// GetTicker returns the current ticker
func (a *ANX) GetTicker(currency string) (Ticker, error) {
var ticker Ticker
var t Ticker
path := fmt.Sprintf("%sapi/2/%s/%s", a.APIUrl, currency, anxTicker)
return ticker, a.SendHTTPRequest(path, &ticker)
return t, a.SendHTTPRequest(path, &t)
}
// GetDepth returns current orderbook depth.
func (a *ANX) GetDepth(currency string) (Depth, error) {
var depth Depth
path := fmt.Sprintf("%sapi/2/%s/%s", a.APIUrl, currency, anxDepth)
return depth, a.SendHTTPRequest(path, &depth)
}
// GetAPIKey returns a new generated API key set.
func (a *ANX) GetAPIKey(username, password, otp, deviceID string) (string, string, error) {
request := make(map[string]interface{})
request["nonce"] = strconv.FormatInt(time.Now().UnixNano(), 10)[0:13]
request["username"] = username
request["password"] = password
func (a *ANX) GetAPIKey(username, password, otp, deviceID string) (apiKey, apiSecret string, err error) {
req := make(map[string]interface{})
req["nonce"] = strconv.FormatInt(time.Now().UnixNano(), 10)[0:13]
req["username"] = username
req["password"] = password
if otp != "" {
request["otp"] = otp
req["otp"] = otp
}
request["deviceId"] = deviceID
req["deviceId"] = deviceID
type APIKeyResponse struct {
APIKey string `json:"apiKey"`
@@ -164,21 +162,23 @@ func (a *ANX) GetAPIKey(username, password, otp, deviceID string) (string, strin
}
var response APIKeyResponse
err := a.SendAuthenticatedHTTPRequest(anxAPIKey, request, &response)
err = a.SendAuthenticatedHTTPRequest(anxAPIKey, req, &response)
if err != nil {
return "", "", err
return apiKey, apiSecret, err
}
if response.ResultCode != "OK" {
return "", "", errors.New("Response code is not OK: " + response.ResultCode)
return apiKey, apiSecret, errors.New("Response code is not OK: " + response.ResultCode)
}
return response.APIKey, response.APISecret, nil
apiKey = response.APIKey
apiSecret = response.APISecret
return apiKey, apiSecret, err
}
// GetDataToken returns token data
func (a *ANX) GetDataToken() (string, error) {
request := make(map[string]interface{})
req := make(map[string]interface{})
type DataTokenResponse struct {
ResultCode string `json:"resultCode"`
@@ -188,7 +188,7 @@ func (a *ANX) GetDataToken() (string, error) {
}
var response DataTokenResponse
err := a.SendAuthenticatedHTTPRequest(anxDataToken, request, &response)
err := a.SendAuthenticatedHTTPRequest(anxDataToken, req, &response)
if err != nil {
return "", err
}
@@ -200,10 +200,10 @@ func (a *ANX) GetDataToken() (string, error) {
}
// NewOrder sends a new order request to the exchange.
func (a *ANX) NewOrder(orderType string, buy bool, tradedCurrency string, tradedCurrencyAmount float64, settlementCurrency string, settlementCurrencyAmount float64, limitPriceSettlement float64,
func (a *ANX) NewOrder(orderType string, buy bool, tradedCurrency string, tradedCurrencyAmount float64, settlementCurrency string, settlementCurrencyAmount, limitPriceSettlement float64,
replace bool, replaceUUID string, replaceIfActive bool) (string, error) {
request := make(map[string]interface{})
req := make(map[string]interface{})
var order Order
order.OrderType = orderType
order.BuyTradedCurrency = buy
@@ -223,7 +223,7 @@ func (a *ANX) NewOrder(orderType string, buy bool, tradedCurrency string, traded
order.ReplaceOnlyIfActive = replaceIfActive
}
request["order"] = order
req["order"] = order
type OrderResponse struct {
OrderID string `json:"orderId"`
@@ -232,7 +232,7 @@ func (a *ANX) NewOrder(orderType string, buy bool, tradedCurrency string, traded
}
var response OrderResponse
err := a.SendAuthenticatedHTTPRequest(anxOrderNew, request, &response)
err := a.SendAuthenticatedHTTPRequest(anxOrderNew, req, &response)
if err != nil {
return "", err
}
@@ -246,11 +246,11 @@ func (a *ANX) NewOrder(orderType string, buy bool, tradedCurrency string, traded
// CancelOrderByIDs cancels orders, requires already knowing order IDs
// There is no existing API call to retrieve orderIds
func (a *ANX) CancelOrderByIDs(orderIds []string) (OrderCancelResponse, error) {
request := make(map[string]interface{})
request["orderIds"] = orderIds
req := make(map[string]interface{})
req["orderIds"] = orderIds
var response OrderCancelResponse
err := a.SendAuthenticatedHTTPRequest(anxOrderCancel, request, &response)
err := a.SendAuthenticatedHTTPRequest(anxOrderCancel, req, &response)
if response.ResultCode != "OK" {
return response, errors.New(response.ResultCode)
}
@@ -260,8 +260,8 @@ func (a *ANX) CancelOrderByIDs(orderIds []string) (OrderCancelResponse, error) {
// GetOrderList retrieves orders from the exchange
func (a *ANX) GetOrderList(isActiveOrdersOnly bool) ([]OrderResponse, error) {
request := make(map[string]interface{})
request["activeOnly"] = isActiveOrdersOnly
req := make(map[string]interface{})
req["activeOnly"] = isActiveOrdersOnly
type OrderListResponse struct {
Timestamp int64 `json:"timestamp"`
@@ -270,7 +270,7 @@ func (a *ANX) GetOrderList(isActiveOrdersOnly bool) ([]OrderResponse, error) {
OrderResponses []OrderResponse `json:"orders"`
}
var response OrderListResponse
err := a.SendAuthenticatedHTTPRequest(anxOrderList, request, &response)
err := a.SendAuthenticatedHTTPRequest(anxOrderList, req, &response)
if err != nil {
return nil, err
}
@@ -285,8 +285,8 @@ func (a *ANX) GetOrderList(isActiveOrdersOnly bool) ([]OrderResponse, error) {
// OrderInfo returns information about a specific order
func (a *ANX) OrderInfo(orderID string) (OrderResponse, error) {
request := make(map[string]interface{})
request["orderId"] = orderID
req := make(map[string]interface{})
req["orderId"] = orderID
type OrderInfoResponse struct {
Order OrderResponse `json:"order"`
@@ -295,7 +295,7 @@ func (a *ANX) OrderInfo(orderID string) (OrderResponse, error) {
}
var response OrderInfoResponse
err := a.SendAuthenticatedHTTPRequest(anxOrderInfo, request, &response)
err := a.SendAuthenticatedHTTPRequest(anxOrderInfo, req, &response)
if err != nil {
return OrderResponse{}, err
@@ -310,13 +310,13 @@ func (a *ANX) OrderInfo(orderID string) (OrderResponse, error) {
// Send withdraws a currency to an address
func (a *ANX) Send(currency, address, otp, amount string) (string, error) {
request := make(map[string]interface{})
request["ccy"] = currency
request["amount"] = amount
request["address"] = address
req := make(map[string]interface{})
req["ccy"] = currency
req["amount"] = amount
req["address"] = address
if otp != "" {
request["otp"] = otp
req["otp"] = otp
}
type SendResponse struct {
@@ -326,7 +326,7 @@ func (a *ANX) Send(currency, address, otp, amount string) (string, error) {
}
var response SendResponse
err := a.SendAuthenticatedHTTPRequest(anxSend, request, &response)
err := a.SendAuthenticatedHTTPRequest(anxSend, req, &response)
if err != nil {
return "", err
@@ -341,9 +341,9 @@ func (a *ANX) Send(currency, address, otp, amount string) (string, error) {
// CreateNewSubAccount generates a new sub account
func (a *ANX) CreateNewSubAccount(currency, name string) (string, error) {
request := make(map[string]interface{})
request["ccy"] = currency
request["customRef"] = name
req := make(map[string]interface{})
req["ccy"] = currency
req["customRef"] = name
type SubaccountResponse struct {
SubAccount string `json:"subAccount"`
@@ -352,7 +352,7 @@ func (a *ANX) CreateNewSubAccount(currency, name string) (string, error) {
}
var response SubaccountResponse
err := a.SendAuthenticatedHTTPRequest(anxSubaccountNew, request, &response)
err := a.SendAuthenticatedHTTPRequest(anxSubaccountNew, req, &response)
if err != nil {
return "", err
@@ -366,12 +366,12 @@ func (a *ANX) CreateNewSubAccount(currency, name string) (string, error) {
}
// GetDepositAddressByCurrency returns a deposit address for a specific currency
func (a *ANX) GetDepositAddressByCurrency(currency, name string, new bool) (string, error) {
request := make(map[string]interface{})
request["ccy"] = currency
func (a *ANX) GetDepositAddressByCurrency(currency, name string, newAddr bool) (string, error) {
req := make(map[string]interface{})
req["ccy"] = currency
if name != "" {
request["subAccount"] = name
req["subAccount"] = name
}
type AddressResponse struct {
@@ -383,11 +383,11 @@ func (a *ANX) GetDepositAddressByCurrency(currency, name string, new bool) (stri
var response AddressResponse
path := anxReceieveAddress
if new {
if newAddr {
path = anxCreateAddress
}
err := a.SendAuthenticatedHTTPRequest(path, request, &response)
err := a.SendAuthenticatedHTTPRequest(path, req, &response)
if err != nil {
return "", err
}
@@ -417,17 +417,17 @@ func (a *ANX) SendAuthenticatedHTTPRequest(path string, params map[string]interf
a.Nonce.Inc()
}
request := make(map[string]interface{})
request["nonce"] = a.Nonce.String()[0:13]
req := make(map[string]interface{})
req["nonce"] = a.Nonce.String()[0:13]
path = fmt.Sprintf("api/%s/%s", anxAPIVersion, path)
for key, value := range params {
request[key] = value
req[key] = value
}
PayloadJSON, err := common.JSONEncode(request)
PayloadJSON, err := common.JSONEncode(req)
if err != nil {
return errors.New("SendAuthenticatedHTTPRequest: Unable to JSON request")
return errors.New("unable to JSON request")
}
if a.Verbose {
@@ -483,7 +483,7 @@ func getInternationalBankWithdrawalFee(currency string, amount float64) float64
if currency == symbol.HKD {
fee = 250 + (WithdrawalFees[currency] * amount)
}
//TODO, other fiat currencies require consultation with ANXPRO
// TODO, other fiat currencies require consultation with ANXPRO
return fee
}

View File

@@ -71,13 +71,13 @@ func TestSetup(t *testing.T) {
if a.Websocket.IsEnabled() {
t.Error("Test Failed - ANX Setup() incorrect values set")
}
if len(a.BaseCurrencies) <= 0 {
if len(a.BaseCurrencies) == 0 {
t.Error("Test Failed - ANX Setup() incorrect values set")
}
if len(a.AvailablePairs) <= 0 {
if len(a.AvailablePairs) == 0 {
t.Error("Test Failed - ANX Setup() incorrect values set")
}
if len(a.EnabledPairs) <= 0 {
if len(a.EnabledPairs) == 0 {
t.Error("Test Failed - ANX Setup() incorrect values set")
}
}

View File

@@ -648,7 +648,7 @@ func (b *Binance) CheckLimit(limit int) error {
return nil
}
}
return errors.New("Incorrect limit values - valid values are 5, 10, 20, 50, 100, 500, 1000")
return errors.New("incorrect limit values - valid values are 5, 10, 20, 50, 100, 500, 1000")
}
// CheckSymbol checks value against a variable list
@@ -659,7 +659,7 @@ func (b *Binance) CheckSymbol(symbol string) error {
return nil
}
}
return errors.New("Incorrect symbol values - please check available pairs in configuration")
return errors.New("incorrect symbol values - please check available pairs in configuration")
}
// CheckIntervals checks value against a variable list
@@ -669,7 +669,7 @@ func (b *Binance) CheckIntervals(interval string) error {
return nil
}
}
return errors.New(`Incorrect interval values - valid values are "1m","3m","5m","15m","30m","1h","2h","4h","6h","8h","12h","1d","3d","1w","1M"`)
return errors.New(`incorrect interval values - valid values are "1m","3m","5m","15m","30m","1h","2h","4h","6h","8h","12h","1d","3d","1w","1M"`)
}
// SetValues sets the default valid values
@@ -766,7 +766,7 @@ func (b *Binance) WithdrawCrypto(asset, address, addressTag, name, amount string
return resp.ID, nil
}
//GetDepositAddressForCurrency retrieves the wallet address for a given currency
// GetDepositAddressForCurrency retrieves the wallet address for a given currency
func (b *Binance) GetDepositAddressForCurrency(currency string) (string, error) {
path := fmt.Sprintf("%s%s", b.APIUrl, depositAddress)

View File

@@ -290,8 +290,8 @@ type NewOrderRequest struct {
Quantity float64
Price float64
NewClientOrderID string
StopPrice float64 //Used with STOP_LOSS, STOP_LOSS_LIMIT, TAKE_PROFIT, and TAKE_PROFIT_LIMIT orders.
IcebergQty float64 //Used with LIMIT, STOP_LOSS_LIMIT, and TAKE_PROFIT_LIMIT to create an iceberg order.
StopPrice float64 // Used with STOP_LOSS, STOP_LOSS_LIMIT, TAKE_PROFIT, and TAKE_PROFIT_LIMIT orders.
IcebergQty float64 // Used with LIMIT, STOP_LOSS_LIMIT, and TAKE_PROFIT_LIMIT to create an iceberg order.
NewOrderRespType string
}

View File

@@ -109,7 +109,7 @@ func (b *Binance) UpdateLocalCache(ob WebsocketDepthStream) error {
priceToBeUpdated.Amount, _ = strconv.ParseFloat(asks.(string), 64)
}
}
updateAsk = append(updateBid, priceToBeUpdated)
updateAsk = append(updateAsk, priceToBeUpdated)
}
updatedTime := time.Unix(ob.Timestamp, 0)
@@ -132,7 +132,7 @@ func (b *Binance) WSConnect() error {
var Dialer websocket.Dialer
var err error
ticker := strings.ToLower(
tick := strings.ToLower(
strings.Replace(
strings.Join(b.EnabledPairs, "@ticker/"), "-", "", -1)) + "@ticker"
trade := strings.ToLower(
@@ -147,7 +147,7 @@ func (b *Binance) WSConnect() error {
wsurl := b.Websocket.GetWebsocketURL() +
"/stream?streams=" +
ticker +
tick +
"/" +
trade +
"/" +
@@ -220,8 +220,7 @@ func (b *Binance) WsHandleData() {
return
}
switch read.Type {
case websocket.TextMessage:
if read.Type == websocket.TextMessage {
multiStreamData := MultiStreamData{}
err = common.JSONDecode(read.Raw, &multiStreamData)
if err != nil {
@@ -230,7 +229,8 @@ func (b *Binance) WsHandleData() {
continue
}
if strings.Contains(multiStreamData.Stream, "trade") {
switch multiStreamData.Stream {
case "trade":
trade := TradeStream{}
err := common.JSONDecode(multiStreamData.Data, &trade)
@@ -264,8 +264,7 @@ func (b *Binance) WsHandleData() {
Side: trade.EventType,
}
continue
} else if strings.Contains(multiStreamData.Stream, "ticker") {
case "ticker":
t := TickerStream{}
err := common.JSONDecode(multiStreamData.Data, &t)
@@ -289,8 +288,7 @@ func (b *Binance) WsHandleData() {
b.Websocket.DataHandler <- wsTicker
continue
} else if strings.Contains(multiStreamData.Stream, "kline") {
case "kline":
kline := KlineStream{}
err := common.JSONDecode(multiStreamData.Data, &kline)
@@ -317,8 +315,7 @@ func (b *Binance) WsHandleData() {
b.Websocket.DataHandler <- wsKline
continue
} else if common.StringContains(multiStreamData.Stream, "depth") {
case "depth":
depth := WebsocketDepthStream{}
err := common.JSONDecode(multiStreamData.Data, &depth)

View File

@@ -76,16 +76,17 @@ func (b *Binance) UpdateTicker(p pair.CurrencyPair, assetType string) (ticker.Pr
for _, x := range b.GetEnabledCurrencies() {
curr := exchange.FormatExchangeCurrency(b.Name, x)
for y := range tick {
if tick[y].Symbol == curr.String() {
tickerPrice.Pair = x
tickerPrice.Ask = tick[y].AskPrice
tickerPrice.Bid = tick[y].BidPrice
tickerPrice.High = tick[y].HighPrice
tickerPrice.Last = tick[y].LastPrice
tickerPrice.Low = tick[y].LowPrice
tickerPrice.Volume = tick[y].Volume
ticker.ProcessTicker(b.Name, x, tickerPrice, assetType)
if tick[y].Symbol != curr.String() {
continue
}
tickerPrice.Pair = x
tickerPrice.Ask = tick[y].AskPrice
tickerPrice.Bid = tick[y].BidPrice
tickerPrice.High = tick[y].HighPrice
tickerPrice.Last = tick[y].LastPrice
tickerPrice.Low = tick[y].LowPrice
tickerPrice.Volume = tick[y].Volume
ticker.ProcessTicker(b.Name, x, tickerPrice, assetType)
}
}
return ticker.GetTicker(b.Name, p, assetType)
@@ -192,13 +193,14 @@ func (b *Binance) SubmitOrder(p pair.CurrencyPair, side exchange.OrderSide, orde
}
var requestParamsOrderType RequestParamsOrderType
if orderType == exchange.MarketOrderType {
switch orderType {
case exchange.MarketOrderType:
requestParamsOrderType = BinanceRequestParamsOrderMarket
} else if orderType == exchange.LimitOrderType {
case exchange.LimitOrderType:
requestParamsOrderType = BinanceRequestParamsOrderLimit
} else {
default:
submitOrderResponse.IsOrderPlaced = false
return submitOrderResponse, errors.New("Unsupported order type")
return submitOrderResponse, errors.New("unsupported order type")
}
var orderRequest = NewOrderRequest{
@@ -306,8 +308,8 @@ func (b *Binance) GetFeeByType(feeBuilder exchange.FeeBuilder) (float64, error)
// GetActiveOrders retrieves any orders that are active/open
func (b *Binance) GetActiveOrders(getOrdersRequest exchange.GetOrdersRequest) ([]exchange.OrderDetail, error) {
if len(getOrdersRequest.Currencies) <= 0 {
return nil, errors.New("At least one currency is required to fetch order history")
if len(getOrdersRequest.Currencies) == 0 {
return nil, errors.New("at least one currency is required to fetch order history")
}
var orders []exchange.OrderDetail
@@ -346,8 +348,8 @@ func (b *Binance) GetActiveOrders(getOrdersRequest exchange.GetOrdersRequest) ([
// GetOrderHistory retrieves account order information
// Can Limit response to specific order status
func (b *Binance) GetOrderHistory(getOrdersRequest exchange.GetOrdersRequest) ([]exchange.OrderDetail, error) {
if len(getOrdersRequest.Currencies) <= 0 {
return nil, errors.New("At least one currency is required to fetch order history")
if len(getOrdersRequest.Currencies) == 0 {
return nil, errors.New("at least one currency is required to fetch order history")
}
var orders []exchange.OrderDetail

View File

@@ -210,43 +210,43 @@ func (b *Bitfinex) GetTicker(symbol string) (Ticker, error) {
}
// GetTickerV2 returns ticker information
func (b *Bitfinex) GetTickerV2(symbol string) (Tickerv2, error) {
func (b *Bitfinex) GetTickerV2(symb string) (Tickerv2, error) {
var response []interface{}
var ticker Tickerv2
var tick Tickerv2
path := fmt.Sprintf("%s/v%s/%s/%s", b.APIUrl, bitfinexAPIVersion2, bitfinexTickerV2, symbol)
path := fmt.Sprintf("%s/v%s/%s/%s", b.APIUrl, bitfinexAPIVersion2, bitfinexTickerV2, symb)
err := b.SendHTTPRequest(path, &response, b.Verbose)
if err != nil {
return ticker, err
return tick, err
}
if len(response) > 10 {
ticker.FlashReturnRate = response[0].(float64)
ticker.Bid = response[1].(float64)
ticker.BidSize = response[2].(float64)
ticker.BidPeriod = int64(response[3].(float64))
ticker.Ask = response[4].(float64)
ticker.AskSize = response[5].(float64)
ticker.AskPeriod = int64(response[6].(float64))
ticker.DailyChange = response[7].(float64)
ticker.DailyChangePerc = response[8].(float64)
ticker.Last = response[9].(float64)
ticker.Volume = response[10].(float64)
ticker.High = response[11].(float64)
ticker.Low = response[12].(float64)
tick.FlashReturnRate = response[0].(float64)
tick.Bid = response[1].(float64)
tick.BidSize = response[2].(float64)
tick.BidPeriod = int64(response[3].(float64))
tick.Ask = response[4].(float64)
tick.AskSize = response[5].(float64)
tick.AskPeriod = int64(response[6].(float64))
tick.DailyChange = response[7].(float64)
tick.DailyChangePerc = response[8].(float64)
tick.Last = response[9].(float64)
tick.Volume = response[10].(float64)
tick.High = response[11].(float64)
tick.Low = response[12].(float64)
} else {
ticker.Bid = response[0].(float64)
ticker.BidSize = response[1].(float64)
ticker.Ask = response[2].(float64)
ticker.AskSize = response[3].(float64)
ticker.DailyChange = response[4].(float64)
ticker.DailyChangePerc = response[5].(float64)
ticker.Last = response[6].(float64)
ticker.Volume = response[7].(float64)
ticker.High = response[8].(float64)
ticker.Low = response[9].(float64)
tick.Bid = response[0].(float64)
tick.BidSize = response[1].(float64)
tick.Ask = response[2].(float64)
tick.AskSize = response[3].(float64)
tick.DailyChange = response[4].(float64)
tick.DailyChangePerc = response[5].(float64)
tick.Last = response[6].(float64)
tick.Volume = response[7].(float64)
tick.High = response[8].(float64)
tick.Low = response[9].(float64)
}
return ticker, nil
return tick, nil
}
// GetTickersV2 returns ticker information for multiple symbols
@@ -438,13 +438,13 @@ func (b *Bitfinex) GetTradesV2(currencyPair string, timestampStart, timestampEnd
if tempHistory.Amount < 0 {
tempHistory.Type = "SELL"
tempHistory.Amount = tempHistory.Amount * -1
tempHistory.Amount *= -1
}
actualHistory = append(actualHistory, tempHistory)
}
//re-order index
// re-order index
if reOrderResp {
orderedHistory := make([]TradeStructureV2, len(actualHistory))
for i, quickRange := range actualHistory {
@@ -521,18 +521,18 @@ func (b *Bitfinex) GetAccountSummary() (AccountSummary, error) {
// NewDeposit returns a new deposit address
// Method - Example methods accepted: “bitcoin”, “litecoin”, “ethereum”,
//“tethers", "ethereumc", "zcash", "monero", "iota", "bcash"
// “tethers", "ethereumc", "zcash", "monero", "iota", "bcash"
// WalletName - accepted: “trading”, “exchange”, “deposit”
// renew - Default is 0. If set to 1, will return a new unused deposit address
func (b *Bitfinex) NewDeposit(method, walletName string, renew int) (DepositResponse, error) {
response := DepositResponse{}
request := make(map[string]interface{})
request["method"] = method
request["wallet_name"] = walletName
request["renew"] = renew
req := make(map[string]interface{})
req["method"] = method
req["wallet_name"] = walletName
req["renew"] = renew
return response,
b.SendAuthenticatedHTTPRequest(http.MethodPost, bitfinexDeposit, request, &response)
b.SendAuthenticatedHTTPRequest(http.MethodPost, bitfinexDeposit, req, &response)
}
// GetKeyPermissions checks the permissions of the key being used to generate
@@ -567,31 +567,31 @@ func (b *Bitfinex) GetAccountBalance() ([]Balance, error) {
// WalletTo - example "deposit"
func (b *Bitfinex) WalletTransfer(amount float64, currency, walletFrom, walletTo string) ([]WalletTransfer, error) {
response := []WalletTransfer{}
request := make(map[string]interface{})
request["amount"] = amount
request["currency"] = currency
request["walletfrom"] = walletFrom
request["walletTo"] = walletTo
req := make(map[string]interface{})
req["amount"] = amount
req["currency"] = currency
req["walletfrom"] = walletFrom
req["walletTo"] = walletTo
return response,
b.SendAuthenticatedHTTPRequest(http.MethodPost, bitfinexTransfer, request, &response)
b.SendAuthenticatedHTTPRequest(http.MethodPost, bitfinexTransfer, req, &response)
}
// WithdrawCryptocurrency requests a withdrawal from one of your wallets.
// For FIAT, use WithdrawFIAT
func (b *Bitfinex) WithdrawCryptocurrency(withdrawType, wallet, address, currency, paymentID string, amount float64) ([]Withdrawal, error) {
response := []Withdrawal{}
request := make(map[string]interface{})
request["withdraw_type"] = withdrawType
request["walletselected"] = wallet
request["amount"] = strconv.FormatFloat(amount, 'f', -1, 64)
request["address"] = address
req := make(map[string]interface{})
req["withdraw_type"] = withdrawType
req["walletselected"] = wallet
req["amount"] = strconv.FormatFloat(amount, 'f', -1, 64)
req["address"] = address
if currency == symbol.XMR {
request["paymend_id"] = paymentID
req["paymend_id"] = paymentID
}
return response,
b.SendAuthenticatedHTTPRequest(http.MethodPost, bitfinexWithdrawal, request, &response)
b.SendAuthenticatedHTTPRequest(http.MethodPost, bitfinexWithdrawal, req, &response)
}
// WithdrawFIAT requests a withdrawal from one of your wallets.
@@ -601,85 +601,85 @@ func (b *Bitfinex) WithdrawFIAT(withdrawType, wallet, wireCurrency,
intermediaryBankName, intermediaryBankAddress, intermediaryBankCity, intermediaryBankCountry, intermediaryBankSwift string,
amount, accountNumber, intermediaryBankAccountNumber float64, isExpressWire, requiresIntermediaryBank bool) ([]Withdrawal, error) {
response := []Withdrawal{}
request := make(map[string]interface{})
request["withdraw_type"] = withdrawType
request["walletselected"] = wallet
request["amount"] = strconv.FormatFloat(amount, 'f', -1, 64)
request["account_name"] = accountName
request["account_number"] = strconv.FormatFloat(accountNumber, 'f', -1, 64)
request["bank_name"] = bankName
request["bank_address"] = bankAddress
request["bank_city"] = bankCity
request["bank_country"] = bankCountry
request["expressWire"] = isExpressWire
request["swift"] = swift
request["detail_payment"] = transactionMessage
request["currency"] = wireCurrency
request["account_address"] = bankAddress
req := make(map[string]interface{})
req["withdraw_type"] = withdrawType
req["walletselected"] = wallet
req["amount"] = strconv.FormatFloat(amount, 'f', -1, 64)
req["account_name"] = accountName
req["account_number"] = strconv.FormatFloat(accountNumber, 'f', -1, 64)
req["bank_name"] = bankName
req["bank_address"] = bankAddress
req["bank_city"] = bankCity
req["bank_country"] = bankCountry
req["expressWire"] = isExpressWire
req["swift"] = swift
req["detail_payment"] = transactionMessage
req["currency"] = wireCurrency
req["account_address"] = bankAddress
if requiresIntermediaryBank {
request["intermediary_bank_name"] = intermediaryBankName
request["intermediary_bank_address"] = intermediaryBankAddress
request["intermediary_bank_city"] = intermediaryBankCity
request["intermediary_bank_country"] = intermediaryBankCountry
request["intermediary_bank_account"] = strconv.FormatFloat(intermediaryBankAccountNumber, 'f', -1, 64)
request["intermediary_bank_swift"] = intermediaryBankSwift
req["intermediary_bank_name"] = intermediaryBankName
req["intermediary_bank_address"] = intermediaryBankAddress
req["intermediary_bank_city"] = intermediaryBankCity
req["intermediary_bank_country"] = intermediaryBankCountry
req["intermediary_bank_account"] = strconv.FormatFloat(intermediaryBankAccountNumber, 'f', -1, 64)
req["intermediary_bank_swift"] = intermediaryBankSwift
}
return response,
b.SendAuthenticatedHTTPRequest(http.MethodPost, bitfinexWithdrawal, request, &response)
b.SendAuthenticatedHTTPRequest(http.MethodPost, bitfinexWithdrawal, req, &response)
}
// NewOrder submits a new order and returns a order information
// Major Upgrade needed on this function to include all query params
func (b *Bitfinex) NewOrder(currencyPair string, amount float64, price float64, buy bool, Type string, hidden bool) (Order, error) {
func (b *Bitfinex) NewOrder(currencyPair string, amount, price float64, buy bool, orderType string, hidden bool) (Order, error) {
response := Order{}
request := make(map[string]interface{})
request["symbol"] = currencyPair
request["amount"] = strconv.FormatFloat(amount, 'f', -1, 64)
request["price"] = strconv.FormatFloat(price, 'f', -1, 64)
request["exchange"] = "bitfinex"
request["type"] = Type
request["is_hidden"] = hidden
req := make(map[string]interface{})
req["symbol"] = currencyPair
req["amount"] = strconv.FormatFloat(amount, 'f', -1, 64)
req["price"] = strconv.FormatFloat(price, 'f', -1, 64)
req["exchange"] = "bitfinex"
req["type"] = orderType
req["is_hidden"] = hidden
if buy {
request["side"] = "buy"
req["side"] = "buy"
} else {
request["side"] = "sell"
req["side"] = "sell"
}
return response,
b.SendAuthenticatedHTTPRequest(http.MethodPost, bitfinexOrderNew, request, &response)
b.SendAuthenticatedHTTPRequest(http.MethodPost, bitfinexOrderNew, req, &response)
}
// NewOrderMulti allows several new orders at once
func (b *Bitfinex) NewOrderMulti(orders []PlaceOrder) (OrderMultiResponse, error) {
response := OrderMultiResponse{}
request := make(map[string]interface{})
request["orders"] = orders
req := make(map[string]interface{})
req["orders"] = orders
return response,
b.SendAuthenticatedHTTPRequest(http.MethodPost, bitfinexOrderNewMulti, request, &response)
b.SendAuthenticatedHTTPRequest(http.MethodPost, bitfinexOrderNewMulti, req, &response)
}
// CancelExistingOrder cancels a single order by OrderID
func (b *Bitfinex) CancelExistingOrder(OrderID int64) (Order, error) {
func (b *Bitfinex) CancelExistingOrder(orderID int64) (Order, error) {
response := Order{}
request := make(map[string]interface{})
request["order_id"] = OrderID
req := make(map[string]interface{})
req["order_id"] = orderID
return response,
b.SendAuthenticatedHTTPRequest(http.MethodPost, bitfinexOrderCancel, request, &response)
b.SendAuthenticatedHTTPRequest(http.MethodPost, bitfinexOrderCancel, req, &response)
}
// CancelMultipleOrders cancels multiple orders
func (b *Bitfinex) CancelMultipleOrders(OrderIDs []int64) (string, error) {
func (b *Bitfinex) CancelMultipleOrders(orderIDs []int64) (string, error) {
response := GenericResponse{}
request := make(map[string]interface{})
request["order_ids"] = OrderIDs
req := make(map[string]interface{})
req["order_ids"] = orderIDs
return response.Result,
b.SendAuthenticatedHTTPRequest(http.MethodPost, bitfinexOrderCancelMulti, request, nil)
b.SendAuthenticatedHTTPRequest(http.MethodPost, bitfinexOrderCancelMulti, req, nil)
}
// CancelAllExistingOrders cancels all active and open orders
@@ -691,45 +691,45 @@ func (b *Bitfinex) CancelAllExistingOrders() (string, error) {
}
// ReplaceOrder replaces an older order with a new order
func (b *Bitfinex) ReplaceOrder(OrderID int64, Symbol string, Amount float64, Price float64, Buy bool, Type string, Hidden bool) (Order, error) {
func (b *Bitfinex) ReplaceOrder(orderID int64, symbol string, amount, price float64, buy bool, orderType string, hidden bool) (Order, error) {
response := Order{}
request := make(map[string]interface{})
request["order_id"] = OrderID
request["symbol"] = Symbol
request["amount"] = strconv.FormatFloat(Amount, 'f', -1, 64)
request["price"] = strconv.FormatFloat(Price, 'f', -1, 64)
request["exchange"] = "bitfinex"
request["type"] = Type
request["is_hidden"] = Hidden
req := make(map[string]interface{})
req["order_id"] = orderID
req["symbol"] = symbol
req["amount"] = strconv.FormatFloat(amount, 'f', -1, 64)
req["price"] = strconv.FormatFloat(price, 'f', -1, 64)
req["exchange"] = "bitfinex"
req["type"] = orderType
req["is_hidden"] = hidden
if Buy {
request["side"] = "buy"
if buy {
req["side"] = "buy"
} else {
request["side"] = "sell"
req["side"] = "sell"
}
return response,
b.SendAuthenticatedHTTPRequest(http.MethodPost, bitfinexOrderCancelReplace, request, &response)
b.SendAuthenticatedHTTPRequest(http.MethodPost, bitfinexOrderCancelReplace, req, &response)
}
// GetOrderStatus returns order status information
func (b *Bitfinex) GetOrderStatus(OrderID int64) (Order, error) {
func (b *Bitfinex) GetOrderStatus(orderID int64) (Order, error) {
orderStatus := Order{}
request := make(map[string]interface{})
request["order_id"] = OrderID
req := make(map[string]interface{})
req["order_id"] = orderID
return orderStatus,
b.SendAuthenticatedHTTPRequest(http.MethodPost, bitfinexOrderStatus, request, &orderStatus)
b.SendAuthenticatedHTTPRequest(http.MethodPost, bitfinexOrderStatus, req, &orderStatus)
}
// GetInactiveOrders returns order status information
func (b *Bitfinex) GetInactiveOrders() ([]Order, error) {
var response []Order
request := make(map[string]interface{})
request["limit"] = "100"
req := make(map[string]interface{})
req["limit"] = "100"
return response,
b.SendAuthenticatedHTTPRequest(http.MethodPost, bitfinexInactiveOrders, request, &response)
b.SendAuthenticatedHTTPRequest(http.MethodPost, bitfinexInactiveOrders, req, &response)
}
// GetOpenOrders returns all active orders and statuses
@@ -749,10 +749,10 @@ func (b *Bitfinex) GetActivePositions() ([]Position, error) {
}
// ClaimPosition allows positions to be claimed
func (b *Bitfinex) ClaimPosition(PositionID int) (Position, error) {
func (b *Bitfinex) ClaimPosition(positionID int) (Position, error) {
response := Position{}
request := make(map[string]interface{})
request["position_id"] = PositionID
req := make(map[string]interface{})
req["position_id"] = positionID
return response,
b.SendAuthenticatedHTTPRequest(http.MethodPost, bitfinexClaimPosition, nil, nil)
@@ -761,103 +761,103 @@ func (b *Bitfinex) ClaimPosition(PositionID int) (Position, error) {
// GetBalanceHistory returns balance history for the account
func (b *Bitfinex) GetBalanceHistory(symbol string, timeSince, timeUntil time.Time, limit int, wallet string) ([]BalanceHistory, error) {
response := []BalanceHistory{}
request := make(map[string]interface{})
request["currency"] = symbol
req := make(map[string]interface{})
req["currency"] = symbol
if !timeSince.IsZero() {
request["since"] = timeSince
req["since"] = timeSince
}
if !timeUntil.IsZero() {
request["until"] = timeUntil
req["until"] = timeUntil
}
if limit > 0 {
request["limit"] = limit
req["limit"] = limit
}
if len(wallet) > 0 {
request["wallet"] = wallet
req["wallet"] = wallet
}
return response,
b.SendAuthenticatedHTTPRequest(http.MethodPost, bitfinexHistory, request, &response)
b.SendAuthenticatedHTTPRequest(http.MethodPost, bitfinexHistory, req, &response)
}
// GetMovementHistory returns an array of past deposits and withdrawals
func (b *Bitfinex) GetMovementHistory(symbol, method string, timeSince, timeUntil time.Time, limit int) ([]MovementHistory, error) {
response := []MovementHistory{}
request := make(map[string]interface{})
request["currency"] = symbol
req := make(map[string]interface{})
req["currency"] = symbol
if len(method) > 0 {
request["method"] = method
req["method"] = method
}
if !timeSince.IsZero() {
request["since"] = timeSince
req["since"] = timeSince
}
if !timeUntil.IsZero() {
request["until"] = timeUntil
req["until"] = timeUntil
}
if limit > 0 {
request["limit"] = limit
req["limit"] = limit
}
return response,
b.SendAuthenticatedHTTPRequest(http.MethodPost, bitfinexHistoryMovements, request, &response)
b.SendAuthenticatedHTTPRequest(http.MethodPost, bitfinexHistoryMovements, req, &response)
}
// GetTradeHistory returns past executed trades
func (b *Bitfinex) GetTradeHistory(currencyPair string, timestamp, until time.Time, limit, reverse int) ([]TradeHistory, error) {
response := []TradeHistory{}
request := make(map[string]interface{})
request["currency"] = currencyPair
request["timestamp"] = timestamp
req := make(map[string]interface{})
req["currency"] = currencyPair
req["timestamp"] = timestamp
if !until.IsZero() {
request["until"] = until
req["until"] = until
}
if limit > 0 {
request["limit"] = limit
req["limit"] = limit
}
if reverse > 0 {
request["reverse"] = reverse
req["reverse"] = reverse
}
return response,
b.SendAuthenticatedHTTPRequest(http.MethodPost, bitfinexTradeHistory, request, &response)
b.SendAuthenticatedHTTPRequest(http.MethodPost, bitfinexTradeHistory, req, &response)
}
// NewOffer submits a new offer
func (b *Bitfinex) NewOffer(symbol string, amount, rate float64, period int64, direction string) (Offer, error) {
response := Offer{}
request := make(map[string]interface{})
request["currency"] = symbol
request["amount"] = amount
request["rate"] = rate
request["period"] = period
request["direction"] = direction
req := make(map[string]interface{})
req["currency"] = symbol
req["amount"] = amount
req["rate"] = rate
req["period"] = period
req["direction"] = direction
return response,
b.SendAuthenticatedHTTPRequest(http.MethodPost, bitfinexOfferNew, request, &response)
b.SendAuthenticatedHTTPRequest(http.MethodPost, bitfinexOfferNew, req, &response)
}
// CancelOffer cancels offer by offerID
func (b *Bitfinex) CancelOffer(OfferID int64) (Offer, error) {
func (b *Bitfinex) CancelOffer(offerID int64) (Offer, error) {
response := Offer{}
request := make(map[string]interface{})
request["offer_id"] = OfferID
req := make(map[string]interface{})
req["offer_id"] = offerID
return response,
b.SendAuthenticatedHTTPRequest(http.MethodPost, bitfinexOfferCancel, request, &response)
b.SendAuthenticatedHTTPRequest(http.MethodPost, bitfinexOfferCancel, req, &response)
}
// GetOfferStatus checks offer status whether it has been cancelled, execute or
// is still active
func (b *Bitfinex) GetOfferStatus(OfferID int64) (Offer, error) {
func (b *Bitfinex) GetOfferStatus(offerID int64) (Offer, error) {
response := Offer{}
request := make(map[string]interface{})
request["offer_id"] = OfferID
req := make(map[string]interface{})
req["offer_id"] = offerID
return response,
b.SendAuthenticatedHTTPRequest(http.MethodPost, bitfinexOrderStatus, request, &response)
b.SendAuthenticatedHTTPRequest(http.MethodPost, bitfinexOrderStatus, req, &response)
}
// GetActiveCredits returns all available credits
@@ -903,13 +903,13 @@ func (b *Bitfinex) GetMarginTotalTakenFunds() ([]MarginTotalTakenFunds, error) {
}
// CloseMarginFunding closes an unused or used taken fund
func (b *Bitfinex) CloseMarginFunding(SwapID int64) (Offer, error) {
func (b *Bitfinex) CloseMarginFunding(swapID int64) (Offer, error) {
response := Offer{}
request := make(map[string]interface{})
request["swap_id"] = SwapID
req := make(map[string]interface{})
req["swap_id"] = swapID
return response,
b.SendAuthenticatedHTTPRequest(http.MethodPost, bitfinexMarginClose, request, &response)
b.SendAuthenticatedHTTPRequest(http.MethodPost, bitfinexMarginClose, req, &response)
}
// SendHTTPRequest sends an unauthenticated request
@@ -930,17 +930,17 @@ func (b *Bitfinex) SendAuthenticatedHTTPRequest(method, path string, params map[
b.Nonce.Inc()
}
request := make(map[string]interface{})
request["request"] = fmt.Sprintf("%s%s", bitfinexAPIVersion, path)
request["nonce"] = b.Nonce.String()
req := make(map[string]interface{})
req["request"] = fmt.Sprintf("%s%s", bitfinexAPIVersion, path)
req["nonce"] = b.Nonce.String()
for key, value := range params {
request[key] = value
req[key] = value
}
PayloadJSON, err := common.JSONEncode(request)
PayloadJSON, err := common.JSONEncode(req)
if err != nil {
return errors.New("SendAuthenticatedHTTPRequest: Unable to JSON request")
return errors.New("sendAuthenticatedAPIRequest: unable to JSON request")
}
if b.Verbose {
@@ -996,14 +996,14 @@ func (b *Bitfinex) GetFee(feeBuilder exchange.FeeBuilder) (float64, error) {
// GetCryptocurrencyWithdrawalFee returns an estimate of fee based on type of transaction
func (b *Bitfinex) GetCryptocurrencyWithdrawalFee(currency string, accountFees AccountFees) (fee float64, err error) {
switch accountFees.Withdraw[currency].(type) {
switch result := accountFees.Withdraw[currency].(type) {
case string:
fee, err = strconv.ParseFloat(accountFees.Withdraw[currency].(string), 64)
fee, err = strconv.ParseFloat(result, 64)
if err != nil {
return 0, err
}
case float64:
fee = accountFees.Withdraw[currency].(float64)
fee = result
}
return fee, nil

View File

@@ -54,10 +54,10 @@ var pongReceive chan struct{}
// WsPingHandler sends a ping request to the websocket server
func (b *Bitfinex) WsPingHandler() error {
request := make(map[string]string)
request["event"] = "ping"
req := make(map[string]string)
req["event"] = "ping"
return b.WsSend(request)
return b.WsSend(req)
}
// WsSend sends data to the websocket server
@@ -71,42 +71,42 @@ func (b *Bitfinex) WsSend(data interface{}) error {
// WsSubscribe subscribes to the websocket channel
func (b *Bitfinex) WsSubscribe(channel string, params map[string]string) error {
request := make(map[string]string)
request["event"] = "subscribe"
request["channel"] = channel
req := make(map[string]string)
req["event"] = "subscribe"
req["channel"] = channel
if len(params) > 0 {
for k, v := range params {
request[k] = v
req[k] = v
}
}
return b.WsSend(request)
return b.WsSend(req)
}
// WsSendAuth sends a autheticated event payload
func (b *Bitfinex) WsSendAuth() error {
request := make(map[string]interface{})
req := make(map[string]interface{})
payload := "AUTH" + strconv.FormatInt(time.Now().UnixNano(), 10)[:13]
request["event"] = "auth"
request["apiKey"] = b.APIKey
req["event"] = "auth"
req["apiKey"] = b.APIKey
request["authSig"] = common.HexEncodeToString(
req["authSig"] = common.HexEncodeToString(
common.GetHMAC(
common.HashSHA512_384,
[]byte(payload),
[]byte(b.APISecret)))
request["authPayload"] = payload
req["authPayload"] = payload
return b.WsSend(request)
return b.WsSend(req)
}
// WsSendUnauth sends an unauthenticated payload
func (b *Bitfinex) WsSendUnauth() error {
request := make(map[string]string)
request["event"] = "unauth"
req := make(map[string]string)
req["event"] = "unauth"
return b.WsSend(request)
return b.WsSend(req)
}
// WsAddSubscriptionChannel adds a new subscription channel to the
@@ -145,12 +145,12 @@ func (b *Bitfinex) WsConnect() error {
b.WebsocketConn, _, err = Dialer.Dial(b.Websocket.GetWebsocketURL(), http.Header{})
if err != nil {
return fmt.Errorf("Unable to connect to Websocket. Error: %s", err)
return fmt.Errorf("unable to connect to Websocket. Error: %s", err)
}
_, resp, err := b.WebsocketConn.ReadMessage()
if err != nil {
return fmt.Errorf("Unable to read from Websocket. Error: %s", err)
return fmt.Errorf("unable to read from Websocket. Error: %s", err)
}
var hs WebsocketHandshake
@@ -234,8 +234,7 @@ func (b *Bitfinex) WsDataHandler() {
return
}
switch stream.Type {
case websocket.TextMessage:
if stream.Type == websocket.TextMessage {
var result interface{}
common.JSONDecode(stream.Raw, &result)
@@ -482,7 +481,7 @@ func (b *Bitfinex) WsDataHandler() {
newAmount := trades[0].Amount
if newAmount < 0 {
side = "SELL"
newAmount = newAmount * -1
newAmount *= -1
}
b.Websocket.DataHandler <- exchange.TradeData{

View File

@@ -243,7 +243,7 @@ func (b *Bitfinex) WithdrawCryptocurrencyFunds(withdrawRequest exchange.Withdraw
return "", err
}
if len(resp) == 0 {
return "", errors.New("No withdrawID returned. Check order status")
return "", errors.New("no withdrawID returned. Check order status")
}
return fmt.Sprintf("%v", resp[0].WithdrawalID), err
@@ -268,7 +268,7 @@ func (b *Bitfinex) WithdrawFiatFunds(withdrawRequest exchange.WithdrawRequest) (
return "", err
}
if len(resp) == 0 {
return "", errors.New("No withdrawID returned. Check order status")
return "", errors.New("no withdrawID returned. Check order status")
}
var withdrawalSuccesses string
@@ -332,13 +332,14 @@ func (b *Bitfinex) GetActiveOrders(getOrdersRequest exchange.GetOrdersRequest) (
ExecutedAmount: order.ExecutedAmount,
}
if order.IsLive {
switch {
case order.IsLive:
orderDetail.Status = string(exchange.ActiveOrderStatus)
} else if order.IsCancelled {
case order.IsCancelled:
orderDetail.Status = string(exchange.CancelledOrderStatus)
} else if order.IsHidden {
case order.IsHidden:
orderDetail.Status = string(exchange.HiddenOrderStatus)
} else {
default:
orderDetail.Status = string(exchange.UnknownOrderStatus)
}
@@ -391,13 +392,14 @@ func (b *Bitfinex) GetOrderHistory(getOrdersRequest exchange.GetOrdersRequest) (
CurrencyPair: pair.NewCurrencyPairFromString(order.Symbol),
}
if order.IsLive {
switch {
case order.IsLive:
orderDetail.Status = string(exchange.ActiveOrderStatus)
} else if order.IsCancelled {
case order.IsCancelled:
orderDetail.Status = string(exchange.CancelledOrderStatus)
} else if order.IsHidden {
case order.IsHidden:
orderDetail.Status = string(exchange.HiddenOrderStatus)
} else {
default:
orderDetail.Status = string(exchange.UnknownOrderStatus)
}

View File

@@ -251,10 +251,10 @@ func (b *Bitflyer) GetExchangeStatus() (string, error) {
// GetChats returns trollbox chat log
// Note: returns vary from instant to infinty
func (b *Bitflyer) GetChats(FromDate string) ([]ChatLog, error) {
func (b *Bitflyer) GetChats(fromDate string) ([]ChatLog, error) {
var resp []ChatLog
v := url.Values{}
v.Set("from_date", FromDate)
v.Set("from_date", fromDate)
path := fmt.Sprintf("%s%s?%s", b.APIUrl, pubGetChats, v.Encode())
return resp, b.SendHTTPRequest(path, &resp)
@@ -386,9 +386,9 @@ func (b *Bitflyer) SendHTTPRequest(path string, result interface{}) error {
// if you have access and update the authenticated requests
// TODO: Fill out this function once API access is obtained
func (b *Bitflyer) SendAuthHTTPRequest() {
//headers := make(map[string]string)
//headers["ACCESS-KEY"] = b.APIKey
//headers["ACCESS-TIMESTAMP"] = strconv.FormatInt(time.Now().UnixNano(), 10)
// headers := make(map[string]string)
// headers["ACCESS-KEY"] = b.APIKey
// headers["ACCESS-TIMESTAMP"] = strconv.FormatInt(time.Now().UnixNano(), 10)
}
// GetFee returns an estimate of fee based on type of transaction
@@ -411,28 +411,22 @@ func (b *Bitflyer) GetFee(feeBuilder exchange.FeeBuilder) (float64, error) {
}
// calculateTradingFee returns fee when performing a trade
func calculateTradingFee(purchasePrice float64, amount float64) float64 {
func calculateTradingFee(purchasePrice, amount float64) float64 {
fee := 0.0015
// bitflyer has fee tiers, but does not disclose them via API, so the largest has to be assumed
return fee * amount * purchasePrice
}
func getDepositFee(bankTransactionType exchange.InternationalBankTransactionType, currency string) (fee float64) {
switch bankTransactionType {
case exchange.WireTransfer:
switch currency {
case symbol.JPY:
fee = 324
}
if bankTransactionType == exchange.WireTransfer && currency == symbol.JPY {
fee = 324
}
return fee
}
func getWithdrawalFee(bankTransactionType exchange.InternationalBankTransactionType, currency string, amount float64) (fee float64) {
switch bankTransactionType {
case exchange.WireTransfer:
switch currency {
case symbol.JPY:
if bankTransactionType == exchange.WireTransfer {
if currency == symbol.JPY {
if amount < 30000 {
fee = 540
} else {

View File

@@ -5,11 +5,10 @@ import (
"testing"
"github.com/thrasher-/gocryptotrader/common"
"github.com/thrasher-/gocryptotrader/currency/symbol"
"github.com/thrasher-/gocryptotrader/exchanges"
"github.com/thrasher-/gocryptotrader/config"
"github.com/thrasher-/gocryptotrader/currency/pair"
"github.com/thrasher-/gocryptotrader/currency/symbol"
exchange "github.com/thrasher-/gocryptotrader/exchanges"
)
// Please supply your own keys here for due diligence testing

View File

@@ -307,7 +307,7 @@ func (b *Bithumb) GetAccountBalance(c string) (FullBalance, error) {
fullBalance.Xcoin[c] = val
default:
return fullBalance, fmt.Errorf("GetAccountBalance error tag name %s unhandled",
return fullBalance, fmt.Errorf("getaccountbalance error tag name %s unhandled",
splitTag)
}
}
@@ -597,7 +597,7 @@ func (b *Bithumb) SendAuthenticatedHTTPRequest(path string, params url.Values, r
err = common.JSONDecode(intermediary, &errCapture)
if err == nil {
if errCapture.Status != "" && errCapture.Status != "0000" {
return fmt.Errorf("SendAuthenticatedHTTPRequest error Code:%s Message:%s",
return fmt.Errorf("sendAuthenticatedAPIRequest error code: %s message:%s",
errCapture.Status,
errCode[errCapture.Status])
}
@@ -627,9 +627,8 @@ func (b *Bithumb) GetFee(feeBuilder exchange.FeeBuilder) (float64, error) {
}
// calculateTradingFee returns fee when performing a trade
func calculateTradingFee(purchasePrice float64, amount float64) float64 {
func calculateTradingFee(purchasePrice, amount float64) float64 {
fee := 0.0015
return fee * amount * purchasePrice
}

View File

@@ -53,7 +53,7 @@ func (b *Bithumb) GetTradingPairs() ([]string, error) {
}
for x := range currencies {
currencies[x] = currencies[x] + "KRW"
currencies[x] += "KRW"
}
return currencies, nil
@@ -136,7 +136,7 @@ func (b *Bithumb) GetAccountInfo() (exchange.AccountInfo, error) {
for key, totalAmount := range bal.Total {
hold, ok := bal.InUse[key]
if !ok {
return info, fmt.Errorf("GetAccountInfo error - in use item not found for currency %s",
return info, fmt.Errorf("getAccountInfo error - in use item not found for currency %s",
key)
}
@@ -270,10 +270,10 @@ func (b *Bithumb) WithdrawCryptocurrencyFunds(withdrawRequest exchange.WithdrawR
// withdrawal is submitted
func (b *Bithumb) WithdrawFiatFunds(withdrawRequest exchange.WithdrawRequest) (string, error) {
if math.Mod(withdrawRequest.Amount, 1) != 0 {
return "", errors.New("KRW withdrawals do not support decimal places")
return "", errors.New("currency KRW does not support decimal places")
}
if withdrawRequest.Currency.String() != symbol.KRW {
return "", errors.New("Only KRW supported")
return "", errors.New("only KRW is supported")
}
bankDetails := fmt.Sprintf("%v_%v", withdrawRequest.BankCode, withdrawRequest.BankName)
bankAccountNumber := strconv.FormatFloat(withdrawRequest.BankAccountNumber, 'f', -1, 64)

View File

@@ -939,8 +939,7 @@ func (b *Bitmex) GetFee(feeBuilder exchange.FeeBuilder) (float64, error) {
var fee float64
var err error
switch feeBuilder.FeeType {
case exchange.CryptocurrencyTradeFee:
if feeBuilder.FeeType == exchange.CryptocurrencyTradeFee {
fee = calculateTradingFee(feeBuilder.PurchasePrice, feeBuilder.Amount, feeBuilder.IsMaker)
}
if fee < 0 {
@@ -950,7 +949,7 @@ func (b *Bitmex) GetFee(feeBuilder exchange.FeeBuilder) (float64, error) {
}
// calculateTradingFee returns the fee for trading any currency on Bittrex
func calculateTradingFee(purchasePrice float64, amount float64, isMaker bool) float64 {
func calculateTradingFee(purchasePrice, amount float64, isMaker bool) float64 {
var fee = 0.000750
if isMaker {

View File

@@ -86,7 +86,7 @@ func StructValsToURLVals(v interface{}) (url.Values, error) {
// APIKeyParams contains all the parameters to send to the API endpoint
type APIKeyParams struct {
//API Key ID (public component).
// API Key ID (public component).
APIKeyID string `json:"apiKeyID,omitempty"`
}
@@ -160,7 +160,7 @@ type ChatSendParams struct {
// VerifyData verifies outgoing data sets
func (p ChatSendParams) VerifyData() error {
if p.ChannelID == 0 || p.Message == "" {
return errors.New("ChatSendParams error params not correctly set")
return errors.New("chatSendParams error params not correctly set")
}
return nil
}
@@ -287,7 +287,7 @@ type OrderNewParams struct {
// are specified.
OrdType string `json:"ordType,omitempty"`
//OrderQty Order quantity in units of the instrument (i.e. contracts).
// OrderQty Order quantity in units of the instrument (i.e. contracts).
OrderQty float64 `json:"orderQty,omitempty"`
// PegOffsetValue - [Optional] trailing offset from the current price for

View File

@@ -206,17 +206,18 @@ func (b *Bitmex) wsHandleIncomingData() {
if decodedResp.Success {
if b.Verbose {
if len(quickCapture) == 3 {
log.Debugf("Bitmex Websocket: Successfully subscribed to %s",
decodedResp.Subscribe)
log.Debugf("%s websocket: Successfully subscribed to %s",
b.Name, decodedResp.Subscribe)
} else {
log.Debugf("Bitmex Websocket: Successfully authenticated websocket connection")
log.Debugf("%s websocket: Successfully authenticated websocket connection",
b.Name)
}
}
continue
}
b.Websocket.DataHandler <- fmt.Errorf("Bitmex websocket error: Unable to subscribe %s",
decodedResp.Subscribe)
b.Websocket.DataHandler <- fmt.Errorf("%s websocket error: Unable to subscribe %s",
b.Name, decodedResp.Subscribe)
} else if _, ok := quickCapture["table"]; ok {
var decodedResp WebsocketMainResponse
@@ -291,8 +292,8 @@ func (b *Bitmex) wsHandleIncomingData() {
b.Websocket.DataHandler <- announcement.Data
default:
b.Websocket.DataHandler <- fmt.Errorf("Bitmex websocket error: Table unknown - %s",
decodedResp.Table)
b.Websocket.DataHandler <- fmt.Errorf("%s websocket error: Table unknown - %s",
b.Name, decodedResp.Table)
}
}
}
@@ -411,15 +412,11 @@ func (b *Bitmex) websocketSubscribe() error {
subscriber.Arguments = append(subscriber.Arguments, bitmexWSAnnouncement)
for _, contract := range contracts {
// Orderbook subscribe
subscriber.Arguments = append(subscriber.Arguments,
bitmexWSOrderbookL2+":"+contract.Pair().String())
// Trade subscribe
subscriber.Arguments = append(subscriber.Arguments,
bitmexWSTrade+":"+contract.Pair().String())
// Orderbook and Trade subscribe
// NOTE more added here in future
subscriber.Arguments = append(subscriber.Arguments,
bitmexWSOrderbookL2+":"+contract.Pair().String(),
bitmexWSTrade+":"+contract.Pair().String())
}
return b.WebsocketConn.WriteJSON(subscriber)
@@ -432,14 +429,11 @@ func (b *Bitmex) websocketSendAuth() error {
hmac := common.GetHMAC(common.HashSHA256,
[]byte("GET/realtime"+newTimestamp),
[]byte(b.APISecret))
signature := common.HexEncodeToString(hmac)
var sendAuth WebsocketRequest
sendAuth.Command = "authKeyExpires"
sendAuth.Arguments = append(sendAuth.Arguments, b.APIKey)
sendAuth.Arguments = append(sendAuth.Arguments, timestamp)
sendAuth.Arguments = append(sendAuth.Arguments, signature)
sendAuth.Arguments = append(sendAuth.Arguments, b.APIKey, timestamp,
signature)
return b.WebsocketConn.WriteJSON(sendAuth)
}

View File

@@ -2,6 +2,7 @@ package bitmex
import (
"errors"
"fmt"
"math"
"sync"
"time"
@@ -63,7 +64,7 @@ func (b *Bitmex) UpdateTicker(p pair.CurrencyPair, assetType string) (ticker.Pri
}
if len(tick) == 0 {
return tickerPrice, errors.New("Bitmex REST error: no ticker return")
return tickerPrice, fmt.Errorf("%s REST error: no ticker return", b.Name)
}
tickerPrice.Pair = p
@@ -153,9 +154,7 @@ func (b *Bitmex) GetAccountInfo() (exchange.AccountInfo, error) {
// GetFundingHistory returns funding history, deposits and
// withdrawals
func (b *Bitmex) GetFundingHistory() ([]exchange.FundHistory, error) {
var fundHistory []exchange.FundHistory
// b.GetFullFundingHistory()
return fundHistory, common.ErrNotYetImplemented
return nil, common.ErrNotYetImplemented
}
// GetExchangeHistory returns historic trade data since exchange opening.

View File

@@ -192,7 +192,7 @@ func getInternationalBankDepositFee(amount float64) float64 {
}
// CalculateTradingFee returns fee on a currency pair
func (b *Bitstamp) CalculateTradingFee(currency string, purchasePrice float64, amount float64) float64 {
func (b *Bitstamp) CalculateTradingFee(currency string, purchasePrice, amount float64) float64 {
var fee float64
switch currency {
@@ -233,7 +233,7 @@ func (b *Bitstamp) GetTicker(currency string, hourly bool) (Ticker, error) {
// GetOrderbook Returns a JSON dictionary with "bids" and "asks". Each is a list
// of open orders and each order is represented as a list holding the price and
//the amount.
// the amount.
func (b *Bitstamp) GetOrderbook(currency string) (Orderbook, error) {
type response struct {
Timestamp int64 `json:"timestamp,string"`
@@ -415,20 +415,20 @@ func (b *Bitstamp) GetOpenOrders(currencyPair string) ([]Order, error) {
}
// GetOrderStatus returns an the status of an order by its ID
func (b *Bitstamp) GetOrderStatus(OrderID int64) (OrderStatus, error) {
func (b *Bitstamp) GetOrderStatus(orderID int64) (OrderStatus, error) {
resp := OrderStatus{}
req := url.Values{}
req.Add("id", strconv.FormatInt(OrderID, 10))
req.Add("id", strconv.FormatInt(orderID, 10))
return resp,
b.SendAuthenticatedHTTPRequest(bitstampAPIOrderStatus, false, req, &resp)
}
// CancelExistingOrder cancels order by ID
func (b *Bitstamp) CancelExistingOrder(OrderID int64) (bool, error) {
func (b *Bitstamp) CancelExistingOrder(orderID int64) (bool, error) {
result := false
var req = url.Values{}
req.Add("id", strconv.FormatInt(OrderID, 10))
req.Add("id", strconv.FormatInt(orderID, 10))
return result,
b.SendAuthenticatedHTTPRequest(bitstampAPICancelOrder, true, req, &result)
@@ -443,7 +443,7 @@ func (b *Bitstamp) CancelAllExistingOrders() (bool, error) {
}
// PlaceOrder places an order on the exchange.
func (b *Bitstamp) PlaceOrder(currencyPair string, price float64, amount float64, buy, market bool) (Order, error) {
func (b *Bitstamp) PlaceOrder(currencyPair string, price, amount float64, buy, market bool) (Order, error) {
var req = url.Values{}
req.Add("amount", strconv.FormatFloat(amount, 'f', -1, 64))
req.Add("price", strconv.FormatFloat(price, 'f', -1, 64))

View File

@@ -254,10 +254,11 @@ func TestGetOpenOrders(t *testing.T) {
func TestGetOrderStatus(t *testing.T) {
t.Parallel()
if b.APIKey == "" || b.APISecret == "" ||
b.APIKey == "Key" || b.APISecret == "Secret" {
if !areTestAPIKeysSet() {
t.Skip()
}
_, err := b.GetOrderStatus(1337)
if err == nil {
t.Error("Test Failed - GetOpenOrders() error")
@@ -284,10 +285,11 @@ func TestCancelAllExistingOrders(t *testing.T) {
func TestPlaceOrder(t *testing.T) {
t.Parallel()
if b.APIKey == "" || b.APISecret == "" ||
b.APIKey == "Key" || b.APISecret == "Secret" {
if !areTestAPIKeysSet() {
t.Skip()
}
_, err := b.PlaceOrder("btcusd", 0.01, 1, true, true)
if err == nil {
t.Error("Test Failed - PlaceOrder() error")
@@ -309,8 +311,8 @@ func TestGetWithdrawalRequests(t *testing.T) {
func TestCryptoWithdrawal(t *testing.T) {
t.Parallel()
if b.APIKey == "" || b.APISecret == "" ||
b.APIKey == "Key" || b.APISecret == "Secret" {
if !areTestAPIKeysSet() {
t.Skip()
}
@@ -340,14 +342,16 @@ func TestGetUnconfirmedBitcoinDeposits(t *testing.T) {
func TestTransferAccountBalance(t *testing.T) {
t.Parallel()
if b.APIKey == "" || b.APISecret == "" ||
b.APIKey == "Key" || b.APISecret == "Secret" {
if !areTestAPIKeysSet() {
t.Skip()
}
_, err := b.TransferAccountBalance(1, "", "", true)
if err == nil {
t.Error("Test Failed - TransferAccountBalance() error", err)
}
_, err = b.TransferAccountBalance(1, "btc", "", false)
if err == nil {
t.Error("Test Failed - TransferAccountBalance() error", err)

View File

@@ -43,8 +43,8 @@ func (b *Bitstamp) Run() {
if pairs[x].Trading != "Enabled" {
continue
}
pair := strings.Split(pairs[x].Name, "/")
currencies = append(currencies, pair[0]+pair[1])
p := strings.Split(pairs[x].Name, "/")
currencies = append(currencies, p[0]+p[1])
}
err = b.UpdateCurrencies(currencies, false, false)
if err != nil {
@@ -128,32 +128,28 @@ func (b *Bitstamp) GetAccountInfo() (exchange.AccountInfo, error) {
return response, err
}
var currencies []exchange.AccountCurrencyInfo
currencies = append(currencies, exchange.AccountCurrencyInfo{
CurrencyName: "BTC",
TotalValue: accountBalance.BTCAvailable,
Hold: accountBalance.BTCReserved,
})
currencies = append(currencies, exchange.AccountCurrencyInfo{
CurrencyName: "XRP",
TotalValue: accountBalance.XRPAvailable,
Hold: accountBalance.XRPReserved,
})
currencies = append(currencies, exchange.AccountCurrencyInfo{
CurrencyName: "USD",
TotalValue: accountBalance.USDAvailable,
Hold: accountBalance.USDReserved,
})
currencies = append(currencies, exchange.AccountCurrencyInfo{
CurrencyName: "EUR",
TotalValue: accountBalance.EURAvailable,
Hold: accountBalance.EURReserved,
})
var currencies = []exchange.AccountCurrencyInfo{
{
CurrencyName: "BTC",
TotalValue: accountBalance.BTCAvailable,
Hold: accountBalance.BTCReserved,
},
{
CurrencyName: "XRP",
TotalValue: accountBalance.XRPAvailable,
Hold: accountBalance.XRPReserved,
},
{
CurrencyName: "USD",
TotalValue: accountBalance.USDAvailable,
Hold: accountBalance.USDReserved,
},
{
CurrencyName: "EUR",
TotalValue: accountBalance.EURAvailable,
Hold: accountBalance.EURReserved,
},
}
response.Accounts = append(response.Accounts, exchange.Account{
Currencies: currencies,
})
@@ -215,7 +211,7 @@ func (b *Bitstamp) CancelOrder(order exchange.OrderCancellation) error {
func (b *Bitstamp) CancelAllOrders(_ exchange.OrderCancellation) (exchange.CancelAllOrdersResponse, error) {
isCancelAllSuccessful, err := b.CancelAllExistingOrders()
if !isCancelAllSuccessful {
err = errors.New("Cancel all failed. Bitstamp provides no further information. Check order status to verify")
err = errors.New("cancel all orders failed. Bitstamp provides no further information. Check order status to verify")
}
return exchange.CancelAllOrdersResponse{}, err
@@ -337,39 +333,42 @@ func (b *Bitstamp) GetOrderHistory(getOrdersRequest exchange.GetOrdersRequest) (
var orders []exchange.OrderDetail
for _, order := range resp {
if order.Type == 2 {
quoteCurrency := ""
baseCurrency := ""
if order.BTC > 0 {
baseCurrency = symbol.BTC
} else if order.XRP > 0 {
baseCurrency = symbol.XRP
} else {
log.Warnf("No quote currency found for OrderID '%v'", order.OrderID)
}
if order.USD > 0 {
quoteCurrency = symbol.USD
} else if order.EUR > 0 {
quoteCurrency = symbol.EUR
} else {
log.Warnf("No quote currency found for OrderID '%v'", order.OrderID)
}
var currPair pair.CurrencyPair
if quoteCurrency != "" && baseCurrency != "" {
currPair = pair.NewCurrencyPairWithDelimiter(baseCurrency, quoteCurrency, b.ConfigCurrencyPairFormat.Delimiter)
}
orderDate := time.Unix(order.Date, 0)
orders = append(orders, exchange.OrderDetail{
ID: fmt.Sprintf("%v", order.OrderID),
OrderDate: orderDate,
Exchange: b.Name,
CurrencyPair: currPair,
})
if order.Type != 2 {
continue
}
quoteCurrency := ""
baseCurrency := ""
switch {
case order.BTC > 0:
baseCurrency = symbol.BTC
case order.XRP > 0:
baseCurrency = symbol.XRP
default:
log.Warnf("no base currency found for OrderID '%v'", order.OrderID)
}
switch {
case order.USD > 0:
quoteCurrency = symbol.USD
case order.EUR > 0:
quoteCurrency = symbol.EUR
default:
log.Warnf("no quote currency found for orderID '%v'", order.OrderID)
}
var currPair pair.CurrencyPair
if quoteCurrency != "" && baseCurrency != "" {
currPair = pair.NewCurrencyPairWithDelimiter(baseCurrency, quoteCurrency, b.ConfigCurrencyPairFormat.Delimiter)
}
orderDate := time.Unix(order.Date, 0)
orders = append(orders, exchange.OrderDetail{
ID: fmt.Sprintf("%v", order.OrderID),
OrderDate: orderDate,
Exchange: b.Name,
CurrencyPair: currPair,
})
}
exchange.FilterOrdersByTickRange(&orders, getOrdersRequest.StartTicks, getOrdersRequest.EndTicks)

View File

@@ -159,19 +159,19 @@ func (b *Bittrex) GetCurrencies() (Currency, error) {
// GetTicker sends a public get request and returns current ticker information
// on the supplied currency. Example currency input param "btc-ltc".
func (b *Bittrex) GetTicker(currencyPair string) (Ticker, error) {
ticker := Ticker{}
tick := Ticker{}
path := fmt.Sprintf("%s/%s?market=%s", b.APIUrl, bittrexAPIGetTicker,
common.StringToUpper(currencyPair),
)
if err := b.SendHTTPRequest(path, &ticker); err != nil {
return ticker, err
if err := b.SendHTTPRequest(path, &tick); err != nil {
return tick, err
}
if !ticker.Success {
return ticker, errors.New(ticker.Message)
if !tick.Success {
return tick, errors.New(tick.Message)
}
return ticker, nil
return tick, nil
}
// GetMarketSummaries is used to get the last 24 hour summary of all active
@@ -553,8 +553,7 @@ func (b *Bittrex) GetWithdrawalFee(currency string) (float64, error) {
}
// calculateTradingFee returns the fee for trading any currency on Bittrex
func calculateTradingFee(purchasePrice float64, amount float64) float64 {
func calculateTradingFee(purchasePrice, amount float64) float64 {
var fee = 0.0025
return fee * purchasePrice * amount
}

View File

@@ -100,16 +100,17 @@ func (b *Bittrex) UpdateTicker(p pair.CurrencyPair, assetType string) (ticker.Pr
for _, x := range b.GetEnabledCurrencies() {
curr := exchange.FormatExchangeCurrency(b.Name, x)
for y := range tick.Result {
if tick.Result[y].MarketName == curr.String() {
tickerPrice.Pair = x
tickerPrice.High = tick.Result[y].High
tickerPrice.Low = tick.Result[y].Low
tickerPrice.Ask = tick.Result[y].Ask
tickerPrice.Bid = tick.Result[y].Bid
tickerPrice.Last = tick.Result[y].Last
tickerPrice.Volume = tick.Result[y].Volume
ticker.ProcessTicker(b.GetName(), x, tickerPrice, assetType)
if tick.Result[y].MarketName != curr.String() {
continue
}
tickerPrice.Pair = x
tickerPrice.High = tick.Result[y].High
tickerPrice.Low = tick.Result[y].Low
tickerPrice.Ask = tick.Result[y].Ask
tickerPrice.Bid = tick.Result[y].Bid
tickerPrice.Last = tick.Result[y].Last
tickerPrice.Volume = tick.Result[y].Volume
ticker.ProcessTicker(b.GetName(), x, tickerPrice, assetType)
}
}
return ticker.GetTicker(b.Name, p, assetType)

View File

@@ -383,12 +383,12 @@ func (b *BTCC) WsProcessOrderbookSnapshot(ob WsOrderbookSnapshot) error {
var asks, bids []orderbook.Item
for _, data := range ob.List {
var newSize float64
switch data.Size.(type) {
switch result := data.Size.(type) {
case float64:
newSize = data.Size.(float64)
newSize = result
case string:
var err error
newSize, err = strconv.ParseFloat(data.Size.(string), 64)
newSize, err = strconv.ParseFloat(result, 64)
if err != nil {
return err
}
@@ -430,12 +430,12 @@ func (b *BTCC) WsProcessOrderbookUpdate(ob WsOrderbookSnapshot) error {
var asks, bids []orderbook.Item
for _, data := range ob.List {
var newSize float64
switch data.Size.(type) {
switch d := data.Size.(type) {
case float64:
newSize = data.Size.(float64)
newSize = d
case string:
var err error
newSize, err = strconv.ParseFloat(data.Size.(string), 64)
newSize, err = strconv.ParseFloat(d, 64)
if err != nil {
return err
}
@@ -485,26 +485,26 @@ func (b *BTCC) WsProcessOldOrderbookSnapshot(ob WsOrderbookSnapshotOld, symbol s
data := ask.([]interface{})
var price, amount float64
switch data[0].(type) {
switch d := data[0].(type) {
case string:
var err error
price, err = strconv.ParseFloat(data[0].(string), 64)
price, err = strconv.ParseFloat(d, 64)
if err != nil {
return err
}
case float64:
price = data[0].(float64)
price = d
}
switch data[0].(type) {
switch d := data[0].(type) {
case string:
var err error
amount, err = strconv.ParseFloat(data[0].(string), 64)
amount, err = strconv.ParseFloat(d, 64)
if err != nil {
return err
}
case float64:
amount = data[0].(float64)
amount = d
}
asks = append(asks, orderbook.Item{
@@ -517,26 +517,26 @@ func (b *BTCC) WsProcessOldOrderbookSnapshot(ob WsOrderbookSnapshotOld, symbol s
data := bid.([]interface{})
var price, amount float64
switch data[1].(type) {
switch d := data[1].(type) {
case string:
var err error
price, err = strconv.ParseFloat(data[1].(string), 64)
price, err = strconv.ParseFloat(d, 64)
if err != nil {
return err
}
case float64:
price = data[1].(float64)
price = d
}
switch data[1].(type) {
switch d := data[1].(type) {
case string:
var err error
amount, err = strconv.ParseFloat(data[1].(string), 64)
amount, err = strconv.ParseFloat(d, 64)
if err != nil {
return err
}
case float64:
amount = data[1].(float64)
amount = d
}
bids = append(bids, orderbook.Item{
@@ -546,7 +546,6 @@ func (b *BTCC) WsProcessOldOrderbookSnapshot(ob WsOrderbookSnapshotOld, symbol s
}
p := pair.NewCurrencyPairFromString(symbol)
err := b.Websocket.Orderbook.Update(bids, asks, p, time.Now(), b.GetName(), "SPOT")
if err != nil {
return err

View File

@@ -1,7 +1,6 @@
package btcc
import (
"errors"
"sync"
"github.com/thrasher-/gocryptotrader/common"
@@ -55,7 +54,7 @@ func (b *BTCC) Run() {
log.Errorf("%s failed to update enabled currencies. %s\n", b.Name, err)
}
err = cfg.UpdateExchangeConfig(exchCfg)
err = cfg.UpdateExchangeConfig(&exchCfg)
if err != nil {
log.Errorf("%s failed to update config. %s\n", b.Name, err)
return
@@ -65,96 +64,44 @@ func (b *BTCC) Run() {
// UpdateTicker updates and returns the ticker for a currency pair
func (b *BTCC) UpdateTicker(p pair.CurrencyPair, assetType string) (ticker.Price, error) {
// var tickerPrice ticker.Price
// tick, err := b.GetTicker(exchange.FormatExchangeCurrency(b.GetName(), p).String())
// if err != nil {
// return tickerPrice, err
// }
// tickerPrice.Pair = p
// tickerPrice.Ask = tick.AskPrice
// tickerPrice.Bid = tick.BidPrice
// tickerPrice.Low = tick.Low
// tickerPrice.Last = tick.Last
// tickerPrice.Volume = tick.Volume24H
// tickerPrice.High = tick.High
// ticker.ProcessTicker(b.GetName(), p, tickerPrice, assetType)
// return ticker.GetTicker(b.Name, p, assetType)
return ticker.Price{}, errors.New("REST NOT SUPPORTED")
return ticker.Price{}, common.ErrFunctionNotSupported
}
// GetTickerPrice returns the ticker for a currency pair
func (b *BTCC) GetTickerPrice(p pair.CurrencyPair, assetType string) (ticker.Price, error) {
// tickerNew, err := ticker.GetTicker(b.GetName(), p, assetType)
// if err != nil {
// return b.UpdateTicker(p, assetType)
// }
// return tickerNew, nil
return ticker.Price{}, errors.New("REST NOT SUPPORTED")
return ticker.Price{}, common.ErrFunctionNotSupported
}
// GetOrderbookEx returns the orderbook for a currency pair
func (b *BTCC) GetOrderbookEx(p pair.CurrencyPair, assetType string) (orderbook.Base, error) {
// ob, err := orderbook.GetOrderbook(b.GetName(), p, assetType)
// if err != nil {
// return b.UpdateOrderbook(p, assetType)
// }
// return ob, nil
return orderbook.Base{}, errors.New("REST NOT SUPPORTED")
return orderbook.Base{}, common.ErrFunctionNotSupported
}
// UpdateOrderbook updates and returns the orderbook for a currency pair
func (b *BTCC) UpdateOrderbook(p pair.CurrencyPair, assetType string) (orderbook.Base, error) {
// var orderBook orderbook.Base
// orderbookNew, err := b.GetOrderBook(exchange.FormatExchangeCurrency(b.GetName(), p).String(), 100)
// if err != nil {
// return orderBook, err
// }
// for x := range orderbookNew.Bids {
// data := orderbookNew.Bids[x]
// orderBook.Bids = append(orderBook.Bids, orderbook.Item{Price: data[0], Amount: data[1]})
// }
// for x := range orderbookNew.Asks {
// data := orderbookNew.Asks[x]
// orderBook.Asks = append(orderBook.Asks, orderbook.Item{Price: data[0], Amount: data[1]})
// }
// orderbook.ProcessOrderbook(b.GetName(), p, orderBook, assetType)
// return orderbook.GetOrderbook(b.Name, p, assetType)
return orderbook.Base{}, errors.New("REST NOT SUPPORTED")
return orderbook.Base{}, common.ErrFunctionNotSupported
}
// GetAccountInfo : Retrieves balances for all enabled currencies for
// the Kraken exchange - TODO
func (b *BTCC) GetAccountInfo() (exchange.AccountInfo, error) {
// var response exchange.AccountInfo
// response.ExchangeName = b.GetName()
// return response, nil
return exchange.AccountInfo{}, errors.New("REST NOT SUPPORTED")
return exchange.AccountInfo{}, common.ErrFunctionNotSupported
}
// GetFundingHistory returns funding history, deposits and
// withdrawals
func (b *BTCC) GetFundingHistory() ([]exchange.FundHistory, error) {
// var fundHistory []exchange.FundHistory
// return fundHistory, common.ErrFunctionNotSupported
return nil, errors.New("REST NOT SUPPORTED")
return nil, common.ErrFunctionNotSupported
}
// GetExchangeHistory returns historic trade data since exchange opening.
func (b *BTCC) GetExchangeHistory(p pair.CurrencyPair, assetType string) ([]exchange.TradeHistory, error) {
// var resp []exchange.TradeHistory
// return resp, common.ErrNotYetImplemented
return nil, errors.New("REST NOT SUPPORTED")
return nil, common.ErrFunctionNotSupported
}
// SubmitOrder submits a new order
func (b *BTCC) SubmitOrder(p pair.CurrencyPair, side exchange.OrderSide, orderType exchange.OrderType, amount, price float64, clientID string) (exchange.SubmitOrderResponse, error) {
var submitOrderResponse exchange.SubmitOrderResponse
return submitOrderResponse, common.ErrNotYetImplemented
return exchange.SubmitOrderResponse{}, common.ErrNotYetImplemented
}
// ModifyOrder will allow of changing orderbook placement and limit to
@@ -175,8 +122,7 @@ func (b *BTCC) CancelAllOrders(orderCancellation exchange.OrderCancellation) (ex
// GetOrderInfo returns information on a current open order
func (b *BTCC) GetOrderInfo(orderID int64) (exchange.OrderDetail, error) {
var orderDetail exchange.OrderDetail
return orderDetail, common.ErrNotYetImplemented
return exchange.OrderDetail{}, common.ErrNotYetImplemented
}
// GetDepositAddress returns a deposit address for a specified currency

View File

@@ -140,13 +140,13 @@ func (b *BTCMarkets) GetMarkets() ([]Market, error) {
// GetTicker returns a ticker
// symbol - example "btc" or "ltc"
func (b *BTCMarkets) GetTicker(firstPair, secondPair string) (Ticker, error) {
ticker := Ticker{}
tick := Ticker{}
path := fmt.Sprintf("%s/market/%s/%s/tick",
b.APIUrl,
common.StringToUpper(firstPair),
common.StringToUpper(secondPair))
return ticker, b.SendHTTPRequest(path, &ticker)
return tick, b.SendHTTPRequest(path, &tick)
}
// GetOrderbook returns current orderbook
@@ -237,19 +237,19 @@ func (b *BTCMarkets) CancelExistingOrder(orderID []int64) ([]ResponseDetails, er
// since - since a time example "33434568724"
// historic - if false just normal Orders open
func (b *BTCMarkets) GetOrders(currency, instrument string, limit, since int64, historic bool) ([]Order, error) {
request := make(map[string]interface{})
req := make(map[string]interface{})
if currency != "" {
request["currency"] = common.StringToUpper(currency)
req["currency"] = common.StringToUpper(currency)
}
if instrument != "" {
request["instrument"] = common.StringToUpper(instrument)
req["instrument"] = common.StringToUpper(instrument)
}
if limit != 0 {
request["limit"] = limit
req["limit"] = limit
}
if since != 0 {
request["since"] = since
req["since"] = since
}
path := btcMarketsOrderOpen
@@ -259,7 +259,7 @@ func (b *BTCMarkets) GetOrders(currency, instrument string, limit, since int64,
resp := Response{}
err := b.SendAuthenticatedRequest(http.MethodPost, path, request, &resp)
err := b.SendAuthenticatedRequest(http.MethodPost, path, req, &resp)
if err != nil {
return nil, err
}
@@ -269,14 +269,14 @@ func (b *BTCMarkets) GetOrders(currency, instrument string, limit, since int64,
}
for _, order := range resp.Orders {
order.Price = order.Price / common.SatoshisPerBTC
order.OpenVolume = order.OpenVolume / common.SatoshisPerBTC
order.Volume = order.Volume / common.SatoshisPerBTC
order.Price /= common.SatoshisPerBTC
order.OpenVolume /= common.SatoshisPerBTC
order.Volume /= common.SatoshisPerBTC
for _, trade := range order.Trades {
trade.Fee = trade.Fee / common.SatoshisPerBTC
trade.Price = trade.Price / common.SatoshisPerBTC
trade.Volume = trade.Volume / common.SatoshisPerBTC
trade.Fee /= common.SatoshisPerBTC
trade.Price /= common.SatoshisPerBTC
trade.Volume /= common.SatoshisPerBTC
}
}
@@ -289,11 +289,11 @@ func (b *BTCMarkets) GetOpenOrders() ([]Order, error) {
Response
Orders []Order `json:"orders"`
}
request := make(map[string]interface{})
req := make(map[string]interface{})
var resp marketsResp
path := fmt.Sprintf("/v2/order/open")
err := b.SendAuthenticatedRequest(http.MethodGet, path, request, &resp)
err := b.SendAuthenticatedRequest(http.MethodGet, path, req, &resp)
if err != nil {
return nil, err
}
@@ -303,14 +303,14 @@ func (b *BTCMarkets) GetOpenOrders() ([]Order, error) {
}
for _, order := range resp.Orders {
order.Price = order.Price / common.SatoshisPerBTC
order.OpenVolume = order.OpenVolume / common.SatoshisPerBTC
order.Volume = order.Volume / common.SatoshisPerBTC
order.Price /= common.SatoshisPerBTC
order.OpenVolume /= common.SatoshisPerBTC
order.Volume /= common.SatoshisPerBTC
for _, trade := range order.Trades {
trade.Fee = trade.Fee / common.SatoshisPerBTC
trade.Price = trade.Price / common.SatoshisPerBTC
trade.Volume = trade.Volume / common.SatoshisPerBTC
trade.Fee /= common.SatoshisPerBTC
trade.Price /= common.SatoshisPerBTC
trade.Volume /= common.SatoshisPerBTC
}
}
@@ -338,14 +338,14 @@ func (b *BTCMarkets) GetOrderDetail(orderID []int64) ([]Order, error) {
}
for i := range resp.Orders {
resp.Orders[i].Price = resp.Orders[i].Price / common.SatoshisPerBTC
resp.Orders[i].OpenVolume = resp.Orders[i].OpenVolume / common.SatoshisPerBTC
resp.Orders[i].Volume = resp.Orders[i].Volume / common.SatoshisPerBTC
resp.Orders[i].Price /= common.SatoshisPerBTC
resp.Orders[i].OpenVolume /= common.SatoshisPerBTC
resp.Orders[i].Volume /= common.SatoshisPerBTC
for x := range resp.Orders[i].Trades {
resp.Orders[i].Trades[x].Fee = resp.Orders[i].Trades[x].Fee / common.SatoshisPerBTC
resp.Orders[i].Trades[x].Price = resp.Orders[i].Trades[x].Price / common.SatoshisPerBTC
resp.Orders[i].Trades[x].Volume = resp.Orders[i].Trades[x].Volume / common.SatoshisPerBTC
resp.Orders[i].Trades[x].Fee /= common.SatoshisPerBTC
resp.Orders[i].Trades[x].Price /= common.SatoshisPerBTC
resp.Orders[i].Trades[x].Volume /= common.SatoshisPerBTC
}
}
return resp.Orders, nil
@@ -362,8 +362,8 @@ func (b *BTCMarkets) GetAccountBalance() ([]AccountBalance, error) {
// All values are returned in Satoshis, even for fiat currencies.
for i := range balance {
balance[i].Balance = balance[i].Balance / common.SatoshisPerBTC
balance[i].PendingFunds = balance[i].PendingFunds / common.SatoshisPerBTC
balance[i].Balance /= common.SatoshisPerBTC
balance[i].PendingFunds /= common.SatoshisPerBTC
}
return balance, nil
}
@@ -431,7 +431,7 @@ func (b *BTCMarkets) SendHTTPRequest(path string, result interface{}) error {
}
// SendAuthenticatedRequest sends an authenticated HTTP request
func (b *BTCMarkets) SendAuthenticatedRequest(reqType, path string, data interface{}, result interface{}) (err error) {
func (b *BTCMarkets) SendAuthenticatedRequest(reqType, path string, data, result interface{}) (err error) {
if !b.AuthenticatedAPISupport {
return fmt.Errorf(exchange.WarningAuthenticatedRequestWithoutCredentialsSet, b.Name)
}
@@ -441,7 +441,7 @@ func (b *BTCMarkets) SendAuthenticatedRequest(reqType, path string, data interfa
} else {
b.Nonce.Inc()
}
var request string
var req string
payload := []byte("")
if data != nil {
@@ -449,15 +449,15 @@ func (b *BTCMarkets) SendAuthenticatedRequest(reqType, path string, data interfa
if err != nil {
return err
}
request = path + "\n" + b.Nonce.String()[0:13] + "\n" + string(payload)
req = path + "\n" + b.Nonce.String()[0:13] + "\n" + string(payload)
} else {
request = path + "\n" + b.Nonce.String()[0:13] + "\n"
req = path + "\n" + b.Nonce.String()[0:13] + "\n"
}
hmac := common.GetHMAC(common.HashSHA512, []byte(request), []byte(b.APISecret))
hmac := common.GetHMAC(common.HashSHA512, []byte(req), []byte(b.APISecret))
if b.Verbose {
log.Debugf("Sending %s request to URL %s with params %s\n", reqType, b.APIUrl+path, request)
log.Debugf("Sending %s request to URL %s with params %s\n", reqType, b.APIUrl+path, req)
}
headers := make(map[string]string)

View File

@@ -285,7 +285,7 @@ func (b *BTCMarkets) WithdrawCryptocurrencyFunds(withdrawRequest exchange.Withdr
// withdrawal is submitted
func (b *BTCMarkets) WithdrawFiatFunds(withdrawRequest exchange.WithdrawRequest) (string, error) {
if withdrawRequest.Currency != symbol.AUD {
return "", errors.New("Only AUD supported for withdrawals")
return "", errors.New("only AUD is supported for withdrawals")
}
return b.WithdrawAUD(withdrawRequest.BankAccountName, fmt.Sprintf("%v", withdrawRequest.BankAccountNumber), withdrawRequest.BankName, fmt.Sprintf("%v", withdrawRequest.BankCode), withdrawRequest.Amount)
}
@@ -363,8 +363,8 @@ func (b *BTCMarkets) GetActiveOrders(getOrdersRequest exchange.GetOrdersRequest)
// GetOrderHistory retrieves account order information
// Can Limit response to specific order status
func (b *BTCMarkets) GetOrderHistory(getOrdersRequest exchange.GetOrdersRequest) ([]exchange.OrderDetail, error) {
if len(getOrdersRequest.Currencies) <= 0 {
return nil, errors.New("Requires at least one currency pair to retrieve history")
if len(getOrdersRequest.Currencies) == 0 {
return nil, errors.New("requires at least one currency pair to retrieve history")
}
var respOrders []Order

View File

@@ -224,11 +224,10 @@ func (c *CoinbasePro) GetOrderbook(symbol string, level int) (interface{}, error
// GetTicker returns ticker by currency pair
// currencyPair - example "BTC-USD"
func (c *CoinbasePro) GetTicker(currencyPair string) (Ticker, error) {
ticker := Ticker{}
tick := Ticker{}
path := fmt.Sprintf(
"%s/%s/%s", c.APIUrl+coinbaseproProducts, currencyPair, coinbaseproTicker)
return ticker, c.SendHTTPRequest(path, &ticker)
return tick, c.SendHTTPRequest(path, &tick)
}
// GetTrades listd the latest trades for a product
@@ -370,30 +369,30 @@ func (c *CoinbasePro) GetHolds(accountID string) ([]AccountHolds, error) {
// postOnly - [optional] Post only flag Invalid when time_in_force is IOC or FOK
func (c *CoinbasePro) PlaceLimitOrder(clientRef string, price, amount float64, side, timeInforce, cancelAfter, productID, stp string, postOnly bool) (string, error) {
resp := GeneralizedOrderResponse{}
request := make(map[string]interface{})
request["type"] = "limit"
request["price"] = strconv.FormatFloat(price, 'f', -1, 64)
request["size"] = strconv.FormatFloat(amount, 'f', -1, 64)
request["side"] = side
request["product_id"] = productID
req := make(map[string]interface{})
req["type"] = "limit"
req["price"] = strconv.FormatFloat(price, 'f', -1, 64)
req["size"] = strconv.FormatFloat(amount, 'f', -1, 64)
req["side"] = side
req["product_id"] = productID
if cancelAfter != "" {
request["cancel_after"] = cancelAfter
req["cancel_after"] = cancelAfter
}
if timeInforce != "" {
request["time_in_foce"] = timeInforce
req["time_in_foce"] = timeInforce
}
if clientRef != "" {
request["client_oid"] = clientRef
req["client_oid"] = clientRef
}
if stp != "" {
request["stp"] = stp
req["stp"] = stp
}
if postOnly {
request["post_only"] = postOnly
req["post_only"] = postOnly
}
err := c.SendAuthenticatedHTTPRequest(http.MethodPost, coinbaseproOrders, request, &resp)
err := c.SendAuthenticatedHTTPRequest(http.MethodPost, coinbaseproOrders, req, &resp)
if err != nil {
return "", err
}
@@ -417,27 +416,27 @@ func (c *CoinbasePro) PlaceLimitOrder(clientRef string, price, amount float64, s
// size - [optional]* Desired amount in BTC
// funds [optional]* Desired amount of quote currency to use
// * One of size or funds is required.
func (c *CoinbasePro) PlaceMarketOrder(clientRef string, size, funds float64, side string, productID, stp string) (string, error) {
func (c *CoinbasePro) PlaceMarketOrder(clientRef string, size, funds float64, side, productID, stp string) (string, error) {
resp := GeneralizedOrderResponse{}
request := make(map[string]interface{})
request["side"] = side
request["product_id"] = productID
request["type"] = "market"
req := make(map[string]interface{})
req["side"] = side
req["product_id"] = productID
req["type"] = "market"
if size != 0 {
request["size"] = strconv.FormatFloat(size, 'f', -1, 64)
req["size"] = strconv.FormatFloat(size, 'f', -1, 64)
}
if funds != 0 {
request["funds"] = strconv.FormatFloat(funds, 'f', -1, 64)
req["funds"] = strconv.FormatFloat(funds, 'f', -1, 64)
}
if clientRef != "" {
request["client_oid"] = clientRef
req["client_oid"] = clientRef
}
if stp != "" {
request["stp"] = stp
req["stp"] = stp
}
err := c.SendAuthenticatedHTTPRequest(http.MethodPost, coinbaseproOrders, request, &resp)
err := c.SendAuthenticatedHTTPRequest(http.MethodPost, coinbaseproOrders, req, &resp)
if err != nil {
return "", err
}
@@ -460,27 +459,27 @@ func (c *CoinbasePro) PlaceMarketOrder(clientRef string, size, funds float64, si
// MARGIN ORDER PARAMS
// size - [optional]* Desired amount in BTC
// funds - [optional]* Desired amount of quote currency to use
func (c *CoinbasePro) PlaceMarginOrder(clientRef string, size, funds float64, side string, productID, stp string) (string, error) {
func (c *CoinbasePro) PlaceMarginOrder(clientRef string, size, funds float64, side, productID, stp string) (string, error) {
resp := GeneralizedOrderResponse{}
request := make(map[string]interface{})
request["side"] = side
request["product_id"] = productID
request["type"] = "margin"
req := make(map[string]interface{})
req["side"] = side
req["product_id"] = productID
req["type"] = "margin"
if size != 0 {
request["size"] = strconv.FormatFloat(size, 'f', -1, 64)
req["size"] = strconv.FormatFloat(size, 'f', -1, 64)
}
if funds != 0 {
request["funds"] = strconv.FormatFloat(funds, 'f', -1, 64)
req["funds"] = strconv.FormatFloat(funds, 'f', -1, 64)
}
if clientRef != "" {
request["client_oid"] = clientRef
req["client_oid"] = clientRef
}
if stp != "" {
request["stp"] = stp
req["stp"] = stp
}
err := c.SendAuthenticatedHTTPRequest(http.MethodPost, coinbaseproOrders, request, &resp)
err := c.SendAuthenticatedHTTPRequest(http.MethodPost, coinbaseproOrders, req, &resp)
if err != nil {
return "", err
}
@@ -501,12 +500,12 @@ func (c *CoinbasePro) CancelExistingOrder(orderID string) error {
// canceled
func (c *CoinbasePro) CancelAllExistingOrders(currencyPair string) ([]string, error) {
var resp []string
request := make(map[string]interface{})
req := make(map[string]interface{})
if len(currencyPair) > 0 {
request["product_id"] = currencyPair
req["product_id"] = currencyPair
}
return resp, c.SendAuthenticatedHTTPRequest(http.MethodDelete, coinbaseproOrders, request, &resp)
return resp, c.SendAuthenticatedHTTPRequest(http.MethodDelete, coinbaseproOrders, req, &resp)
}
// GetOrders lists current open orders. Only open or un-settled orders are
@@ -521,7 +520,7 @@ func (c *CoinbasePro) GetOrders(status []string, currencyPair string) ([]General
for _, individualStatus := range status {
params.Add("status", individualStatus)
}
if len(currencyPair) != 0 {
if currencyPair != "" {
params.Set("product_id", currencyPair)
}
@@ -545,13 +544,13 @@ func (c *CoinbasePro) GetFills(orderID, currencyPair string) ([]FillResponse, er
resp := []FillResponse{}
params := url.Values{}
if len(orderID) != 0 {
if orderID != "" {
params.Set("order_id", orderID)
}
if len(currencyPair) != 0 {
if currencyPair != "" {
params.Set("product_id", currencyPair)
}
if len(params.Get("order_id")) == 0 && len(params.Get("product_id")) == 0 {
if params.Get("order_id") == "" && params.Get("product_id") == "" {
return resp, errors.New("no parameters set")
}
@@ -578,7 +577,7 @@ func (c *CoinbasePro) GetFundingRecords(status string) ([]Funding, error) {
c.SendAuthenticatedHTTPRequest(http.MethodGet, uri[1:], nil, &resp)
}
////////////////////////// Not receiving reply from server /////////////////
// //////////////////////// Not receiving reply from server /////////////////
// RepayFunding repays the older funding records first
//
// amount - amount of currency to repay
@@ -606,14 +605,14 @@ func (c *CoinbasePro) GetFundingRecords(status string) ([]Funding, error) {
// currency - currency to transfer, currently on "BTC" or "USD"
func (c *CoinbasePro) MarginTransfer(amount float64, transferType, profileID, currency string) (MarginTransfer, error) {
resp := MarginTransfer{}
request := make(map[string]interface{})
request["type"] = transferType
request["amount"] = strconv.FormatFloat(amount, 'f', -1, 64)
request["currency"] = currency
request["margin_profile_id"] = profileID
req := make(map[string]interface{})
req["type"] = transferType
req["amount"] = strconv.FormatFloat(amount, 'f', -1, 64)
req["currency"] = currency
req["margin_profile_id"] = profileID
return resp,
c.SendAuthenticatedHTTPRequest(http.MethodPost, coinbaseproMarginTransfer, request, &resp)
c.SendAuthenticatedHTTPRequest(http.MethodPost, coinbaseproMarginTransfer, req, &resp)
}
// GetPosition returns an overview of account profile.
@@ -628,11 +627,11 @@ func (c *CoinbasePro) GetPosition() (AccountOverview, error) {
// repayOnly - allows the position to be repaid
func (c *CoinbasePro) ClosePosition(repayOnly bool) (AccountOverview, error) {
resp := AccountOverview{}
request := make(map[string]interface{})
request["repay_only"] = repayOnly
req := make(map[string]interface{})
req["repay_only"] = repayOnly
return resp,
c.SendAuthenticatedHTTPRequest(http.MethodPost, coinbaseproPositionClose, request, &resp)
c.SendAuthenticatedHTTPRequest(http.MethodPost, coinbaseproPositionClose, req, &resp)
}
// GetPayMethods returns a full list of payment methods
@@ -695,7 +694,7 @@ func (c *CoinbasePro) WithdrawViaPaymentMethod(amount float64, currency, payment
c.SendAuthenticatedHTTPRequest(http.MethodPost, coinbaseproWithdrawalPaymentMethod, req, &resp)
}
///////////////////////// NO ROUTE FOUND ERROR ////////////////////////////////
// /////////////////////// NO ROUTE FOUND ERROR ////////////////////////////////
// WithdrawViaCoinbase withdraws funds to a coinbase account.
//
// amount - The amount to withdraw
@@ -750,27 +749,27 @@ func (c *CoinbasePro) GetCoinbaseAccounts() ([]CoinbaseAccounts, error) {
// email - [optional] Email address to send the report to
func (c *CoinbasePro) GetReport(reportType, startDate, endDate, currencyPair, accountID, format, email string) (Report, error) {
resp := Report{}
request := make(map[string]interface{})
request["type"] = reportType
request["start_date"] = startDate
request["end_date"] = endDate
request["format"] = "pdf"
req := make(map[string]interface{})
req["type"] = reportType
req["start_date"] = startDate
req["end_date"] = endDate
req["format"] = "pdf"
if len(currencyPair) != 0 {
request["product_id"] = currencyPair
if currencyPair != "" {
req["product_id"] = currencyPair
}
if len(accountID) != 0 {
request["account_id"] = accountID
if accountID != "" {
req["account_id"] = accountID
}
if format == "csv" {
request["format"] = format
req["format"] = format
}
if len(email) != 0 {
request["email"] = email
if email != "" {
req["email"] = email
}
return resp,
c.SendAuthenticatedHTTPRequest(http.MethodPost, coinbaseproReports, request, &resp)
c.SendAuthenticatedHTTPRequest(http.MethodPost, coinbaseproReports, req, &resp)
}
// GetReportStatus once a report request has been accepted for processing, the
@@ -807,7 +806,7 @@ func (c *CoinbasePro) SendAuthenticatedHTTPRequest(method, path string, params m
if params != nil {
payload, err = common.JSONEncode(params)
if err != nil {
return errors.New("SendAuthenticatedHTTPRequest: Unable to JSON request")
return errors.New("sendAuthenticatedHTTPRequest: Unable to JSON request")
}
if c.Verbose {
@@ -855,19 +854,19 @@ func (c *CoinbasePro) calculateTradingFee(trailingVolume []Volume, firstCurrency
var fee float64
for _, i := range trailingVolume {
if strings.EqualFold(i.ProductID, firstCurrency+delimiter+secondCurrency) {
if isMaker {
switch {
case isMaker:
fee = 0
} else if i.Volume <= 10000000 {
case i.Volume <= 10000000:
fee = 0.003
} else if i.Volume > 10000000 && i.Volume <= 100000000 {
case i.Volume > 10000000 && i.Volume <= 100000000:
fee = 0.002
} else if i.Volume > 100000000 {
case i.Volume > 100000000:
fee = 0.001
}
break
}
}
return fee * amount * purchasePrice
}

View File

@@ -16,7 +16,7 @@ var c CoinbasePro
const (
apiKey = ""
apiSecret = ""
clientID = "" //passphrase you made at API CREATION
clientID = "" // passphrase you made at API CREATION
canManipulateRealOrders = false
)

View File

@@ -28,30 +28,29 @@ func (c *CoinbasePro) WebsocketSubscriber() error {
currencies = append(currencies, currency)
}
var channels []WsChannels
channels = append(channels, WsChannels{
Name: "heartbeat",
ProductIDs: currencies,
})
channels = append(channels, WsChannels{
Name: "ticker",
ProductIDs: currencies,
})
channels = append(channels, WsChannels{
Name: "level2",
ProductIDs: currencies,
})
var channels = []WsChannels{
{
Name: "heartbeat",
ProductIDs: currencies,
},
{
Name: "ticker",
ProductIDs: currencies,
},
{
Name: "level2",
ProductIDs: currencies,
},
}
subscribe := WebsocketSubscribe{Type: "subscribe", Channels: channels}
json, err := common.JSONEncode(subscribe)
data, err := common.JSONEncode(subscribe)
if err != nil {
return err
}
return c.WebsocketConn.WriteMessage(websocket.TextMessage, json)
return c.WebsocketConn.WriteMessage(websocket.TextMessage, data)
}
// WsConnect initiates a websocket connection

View File

@@ -158,13 +158,14 @@ func (c *CoinbasePro) SubmitOrder(p pair.CurrencyPair, side exchange.OrderSide,
var submitOrderResponse exchange.SubmitOrderResponse
var response string
var err error
if orderType == exchange.MarketOrderType {
response, err = c.PlaceMarginOrder("", amount, amount, side.ToString(), p.Pair().String(), "")
} else if orderType == exchange.LimitOrderType {
switch orderType {
case exchange.MarketOrderType:
response, err = c.PlaceMarginOrder("", amount, amount, side.ToString(), p.Pair().String(), "")
case exchange.LimitOrderType:
response, err = c.PlaceLimitOrder("", price, amount, side.ToString(), "", "", p.Pair().String(), "", false)
} else {
err = errors.New("not supported")
default:
err = errors.New("order type not supported")
}
if response != "" {
@@ -229,8 +230,8 @@ func (c *CoinbasePro) WithdrawFiatFunds(withdrawRequest exchange.WithdrawRequest
break
}
}
if len(selectedWithdrawalMethod.ID) <= 0 {
return "", fmt.Errorf("Could not find payment method '%v'. Check the name via the website and try again", withdrawRequest.BankName)
if selectedWithdrawalMethod.ID == "" {
return "", fmt.Errorf("could not find payment method '%v'. Check the name via the website and try again", withdrawRequest.BankName)
}
resp, err := c.WithdrawViaPaymentMethod(withdrawRequest.Amount, withdrawRequest.Currency.String(), selectedWithdrawalMethod.ID)

View File

@@ -8,6 +8,7 @@ import (
"net/http"
"time"
"github.com/thrasher-/gocryptotrader/currency/pair"
"github.com/gorilla/websocket"
"github.com/thrasher-/gocryptotrader/common"
"github.com/thrasher-/gocryptotrader/config"
@@ -56,7 +57,7 @@ func (c *COINUT) SetDefaults() {
c.Name = "COINUT"
c.Enabled = false
c.Verbose = false
c.TakerFee = 0.1 //spot
c.TakerFee = 0.1 // spot
c.MakerFee = 0
c.Verbose = false
c.RESTPollingDelay = 10
@@ -286,7 +287,7 @@ func (c *COINUT) GetIndexTicker(asset string) (IndexTicker, error) {
// GetDerivativeInstruments returns a list of derivative instruments
func (c *COINUT) GetDerivativeInstruments(secType string) (interface{}, error) {
var result interface{} //to-do
var result interface{} // to-do
params := make(map[string]interface{})
params["sec_type"] = secType
@@ -331,7 +332,7 @@ func (c *COINUT) GetOpenPositions(instrumentID int) ([]OpenPosition, error) {
c.SendHTTPRequest(coinutPositionOpen, params, true, &result)
}
//to-do: user position update via websocket
// to-do: user position update via websocket
// SendHTTPRequest sends either an authenticated or unauthenticated HTTP request
func (c *COINUT) SendHTTPRequest(apiRequest string, params map[string]interface{}, authenticated bool, result interface{}) (err error) {
@@ -353,7 +354,7 @@ func (c *COINUT) SendHTTPRequest(apiRequest string, params map[string]interface{
payload, err := common.JSONEncode(params)
if err != nil {
return errors.New("SenddHTTPRequest: Unable to JSON request")
return errors.New("sendHTTPRequest: Unable to JSON request")
}
if c.Verbose {
@@ -409,12 +410,13 @@ func (c *COINUT) GetFee(feeBuilder exchange.FeeBuilder) (float64, error) {
func (c *COINUT) calculateTradingFee(firstCurrency, secondCurrency string, purchasePrice, amount float64, isMaker bool) float64 {
var fee float64
if isMaker {
switch {
case isMaker:
fee = 0
} else if currency.IsCryptocurrency(firstCurrency) && !currency.IsCryptocurrency(secondCurrency) ||
!currency.IsCryptocurrency(firstCurrency) && currency.IsCryptocurrency(secondCurrency) {
case currency.IsCryptoFiatPair(pair.NewCurrencyPair(firstCurrency, secondCurrency)):
fee = 0.002
} else {
default:
fee = 0.001
}
@@ -424,19 +426,20 @@ func (c *COINUT) calculateTradingFee(firstCurrency, secondCurrency string, purch
func getInternationalBankWithdrawalFee(currency string, amount float64) float64 {
var fee float64
if currency == symbol.USD {
switch currency {
case symbol.USD:
if amount*0.001 < 10 {
fee = 10
} else {
fee = amount * 0.001
}
} else if currency == symbol.CAD {
case symbol.CAD:
if amount*0.005 < 10 {
fee = 2
} else {
fee = amount * 0.005
}
} else if currency == symbol.SGD {
case symbol.SGD:
if amount*0.001 < 10 {
fee = 10
} else {

View File

@@ -230,7 +230,7 @@ func (c *COINUT) GetNonce() int64 {
// WsSetInstrumentList fetches instrument list and propagates a local cache
func (c *COINUT) WsSetInstrumentList() error {
request, err := common.JSONEncode(wsRequest{
req, err := common.JSONEncode(wsRequest{
Request: "inst_list",
SecType: "SPOT",
Nonce: c.GetNonce(),
@@ -240,7 +240,7 @@ func (c *COINUT) WsSetInstrumentList() error {
return err
}
err = c.WebsocketConn.WriteMessage(websocket.TextMessage, request)
err = c.WebsocketConn.WriteMessage(websocket.TextMessage, req)
if err != nil {
return err
}
@@ -292,14 +292,14 @@ func (c *COINUT) WsSubscribe() error {
return err
}
orderbook := wsRequest{
ob := wsRequest{
Request: "inst_order_book",
InstID: instrumentListByString[p.Pair().String()],
Subscribe: true,
Nonce: c.GetNonce(),
}
objson, err := common.JSONEncode(orderbook)
objson, err := common.JSONEncode(ob)
if err != nil {
return err
}

View File

@@ -62,77 +62,64 @@ func (c *COINUT) GetAccountInfo() (exchange.AccountInfo, error) {
return info, err
}
var balances []exchange.AccountCurrencyInfo
balances = append(balances, exchange.AccountCurrencyInfo{
CurrencyName: symbol.BCH,
TotalValue: bal.BCH,
})
balances = append(balances, exchange.AccountCurrencyInfo{
CurrencyName: symbol.BTC,
TotalValue: bal.BTC,
})
balances = append(balances, exchange.AccountCurrencyInfo{
CurrencyName: symbol.BTG,
TotalValue: bal.BTG,
})
balances = append(balances, exchange.AccountCurrencyInfo{
CurrencyName: symbol.CAD,
TotalValue: bal.CAD,
})
balances = append(balances, exchange.AccountCurrencyInfo{
CurrencyName: symbol.ETC,
TotalValue: bal.ETC,
})
balances = append(balances, exchange.AccountCurrencyInfo{
CurrencyName: symbol.ETH,
TotalValue: bal.ETH,
})
balances = append(balances, exchange.AccountCurrencyInfo{
CurrencyName: symbol.LCH,
TotalValue: bal.LCH,
})
balances = append(balances, exchange.AccountCurrencyInfo{
CurrencyName: symbol.LTC,
TotalValue: bal.LTC,
})
balances = append(balances, exchange.AccountCurrencyInfo{
CurrencyName: symbol.MYR,
TotalValue: bal.MYR,
})
balances = append(balances, exchange.AccountCurrencyInfo{
CurrencyName: symbol.SGD,
TotalValue: bal.SGD,
})
balances = append(balances, exchange.AccountCurrencyInfo{
CurrencyName: symbol.USD,
TotalValue: bal.USD,
})
balances = append(balances, exchange.AccountCurrencyInfo{
CurrencyName: symbol.USDT,
TotalValue: bal.USDT,
})
balances = append(balances, exchange.AccountCurrencyInfo{
CurrencyName: symbol.XMR,
TotalValue: bal.XMR,
})
balances = append(balances, exchange.AccountCurrencyInfo{
CurrencyName: symbol.ZEC,
TotalValue: bal.ZEC,
})
var balances = []exchange.AccountCurrencyInfo{
{
CurrencyName: symbol.BCH,
TotalValue: bal.BCH,
},
{
CurrencyName: symbol.BTC,
TotalValue: bal.BTC,
},
{
CurrencyName: symbol.BTG,
TotalValue: bal.BTG,
},
{
CurrencyName: symbol.CAD,
TotalValue: bal.CAD,
},
{
CurrencyName: symbol.ETC,
TotalValue: bal.ETC,
},
{
CurrencyName: symbol.ETH,
TotalValue: bal.ETH,
},
{
CurrencyName: symbol.LCH,
TotalValue: bal.LCH,
},
{
CurrencyName: symbol.LTC,
TotalValue: bal.LTC,
},
{
CurrencyName: symbol.MYR,
TotalValue: bal.MYR,
},
{
CurrencyName: symbol.SGD,
TotalValue: bal.SGD,
},
{
CurrencyName: symbol.USD,
TotalValue: bal.USD,
},
{
CurrencyName: symbol.USDT,
TotalValue: bal.USDT,
},
{
CurrencyName: symbol.XMR,
TotalValue: bal.XMR,
},
{
CurrencyName: symbol.ZEC,
TotalValue: bal.ZEC,
},
}
info.Exchange = c.GetName()
info.Accounts = append(info.Accounts, exchange.Account{
Currencies: balances,
@@ -233,11 +220,12 @@ func (c *COINUT) SubmitOrder(p pair.CurrencyPair, side exchange.OrderSide, order
currencyArray := instruments.Instruments[p.Pair().String()]
currencyID := currencyArray[0].InstID
if orderType == exchange.LimitOrderType {
switch orderType {
case exchange.LimitOrderType:
APIresponse, err = c.NewOrder(currencyID, amount, price, isBuyOrder, clientIDUint)
} else if orderType == exchange.MarketOrderType {
case exchange.MarketOrderType:
APIresponse, err = c.NewOrder(currencyID, amount, 0, isBuyOrder, clientIDUint)
} else {
default:
return submitOrderResponse, errors.New("unsupported order type")
}
@@ -251,7 +239,7 @@ func (c *COINUT) SubmitOrder(p pair.CurrencyPair, side exchange.OrderSide, order
case OrderRejectResponse:
orderResult := apiResp
submitOrderResponse.OrderID = fmt.Sprintf("%v", orderResult.OrderID)
err = fmt.Errorf("OrderID: %v was rejected: %v", orderResult.OrderID, orderResult.Reasons)
err = fmt.Errorf("orderID: %v was rejected: %v", orderResult.OrderID, orderResult.Reasons)
}
if err == nil {

View File

@@ -21,11 +21,11 @@ import (
)
const (
warningBase64DecryptSecretKeyFailed = "WARNING -- Exchange %s unable to base64 decode secret key.. Disabling Authenticated API support."
warningBase64DecryptSecretKeyFailed = "exchange %s unable to base64 decode secret key.. Disabling Authenticated API support" // nolint:gosec
// WarningAuthenticatedRequestWithoutCredentialsSet error message for authenticated request without credentials set
WarningAuthenticatedRequestWithoutCredentialsSet = "WARNING -- Exchange %s authenticated HTTP request called but not supported due to unset/default API keys."
WarningAuthenticatedRequestWithoutCredentialsSet = "exchange %s authenticated HTTP request called but not supported due to unset/default API keys"
// ErrExchangeNotFound is a stand for an error message
ErrExchangeNotFound = "Exchange not found in dataset"
ErrExchangeNotFound = "exchange not found in dataset"
// DefaultHTTPTimeout is the default HTTP/HTTPS Timeout for exchange requests
DefaultHTTPTimeout = time.Second * 15
)
@@ -77,7 +77,7 @@ type SubmitOrderResponse struct {
// FeeBuilder is the type which holds all parameters required to calculate a fee for an exchange
type FeeBuilder struct {
FeeType FeeType
//Used for calculating crypto trading fees, deposits & withdrawals
// Used for calculating crypto trading fees, deposits & withdrawals
FirstCurrency string
SecondCurrency string
Delimiter string
@@ -439,7 +439,7 @@ func (e *Base) SetAutoPairDefaults() error {
}
if update {
return cfg.UpdateExchangeConfig(exch)
return cfg.UpdateExchangeConfig(&exch)
}
return nil
}
@@ -470,12 +470,12 @@ func (e *Base) SetAssetTypes() error {
exch.AssetTypes = common.JoinStrings(e.AssetTypes, ",")
update = true
} else {
exch.AssetTypes = common.JoinStrings(e.AssetTypes, ",")
e.AssetTypes = common.SplitStrings(exch.AssetTypes, ",")
update = true
}
if update {
return cfg.UpdateExchangeConfig(exch)
return cfg.UpdateExchangeConfig(&exch)
}
return nil
@@ -571,7 +571,7 @@ func (e *Base) SetCurrencyPairFormat() error {
}
if update {
return cfg.UpdateExchangeConfig(exch)
return cfg.UpdateExchangeConfig(&exch)
}
return nil
}
@@ -676,23 +676,23 @@ func (e *Base) IsEnabled() bool {
}
// SetAPIKeys is a method that sets the current API keys for the exchange
func (e *Base) SetAPIKeys(APIKey, APISecret, ClientID string, b64Decode bool) {
func (e *Base) SetAPIKeys(apiKey, apiSecret, clientID string, b64Decode bool) {
if !e.AuthenticatedAPISupport {
return
}
e.APIKey = APIKey
e.ClientID = ClientID
e.APIKey = apiKey
e.ClientID = clientID
if b64Decode {
result, err := common.Base64Decode(APISecret)
result, err := common.Base64Decode(apiSecret)
if err != nil {
e.AuthenticatedAPISupport = false
log.Warn(warningBase64DecryptSecretKeyFailed, e.Name)
}
e.APISecret = string(result)
} else {
e.APISecret = APISecret
e.APISecret = apiSecret
}
}
@@ -723,7 +723,7 @@ func (e *Base) SetCurrencies(pairs []pair.CurrencyPair, enabledPairs bool) error
e.AvailablePairs = pairsStr
}
return cfg.UpdateExchangeConfig(exchCfg)
return cfg.UpdateExchangeConfig(&exchCfg)
}
// UpdateCurrencies updates the exchange currency pairs for either enabledPairs or
@@ -779,7 +779,7 @@ func (e *Base) UpdateCurrencies(exchangeProducts []string, enabled, force bool)
exch.AvailablePairs = common.JoinStrings(products, ",")
e.AvailablePairs = products
}
return cfg.UpdateExchangeConfig(exch)
return cfg.UpdateExchangeConfig(&exch)
}
return nil
}
@@ -860,7 +860,7 @@ func (o OrderSide) ToString() string {
// SetAPIURL sets configuration API URL for an exchange
func (e *Base) SetAPIURL(ec config.ExchangeConfig) error {
if ec.APIURL == "" || ec.APIURLSecondary == "" {
return errors.New("SetAPIURL error variable zero value")
return errors.New("empty config API URLs")
}
if ec.APIURL != config.APIURLNonDefaultMessage {
e.APIUrl = ec.APIURL
@@ -1039,7 +1039,7 @@ func FilterOrdersByTickRange(orders *[]OrderDetail, startTicks, endTicks time.Ti
// FilterOrdersByCurrencies removes any OrderDetails that do not match the provided currency list
// It is forgiving in that the provided currencies can match quote or base currencies
func FilterOrdersByCurrencies(orders *[]OrderDetail, currencies []pair.CurrencyPair) {
if len(currencies) <= 0 {
if len(currencies) == 0 {
return
}

View File

@@ -14,6 +14,11 @@ import (
"github.com/thrasher-/gocryptotrader/exchanges/ticker"
)
const (
defaultTestExchange = "ANX"
defaultTestCurrencyPair = "BTC-USD"
)
func TestSupportsRESTTickerBatchUpdates(t *testing.T) {
b := Base{
Name: "RAWR",
@@ -133,7 +138,7 @@ func TestSetAutoPairDefaults(t *testing.T) {
}
exch.SupportsAutoPairUpdates = false
err = cfg.UpdateExchangeConfig(exch)
err = cfg.UpdateExchangeConfig(&exch)
if err != nil {
t.Fatalf("Test failed. TestSetAutoPairDefaults update config failed. Error %s", err)
}
@@ -211,7 +216,7 @@ func TestSetAssetTypes(t *testing.T) {
t.Fatal("Test failed. TestSetAssetTypes returned nil error for a non-existent exchange")
}
b.Name = "ANX"
b.Name = defaultTestExchange
b.AssetTypes = []string{"SPOT"}
err = b.SetAssetTypes()
if err != nil {
@@ -224,7 +229,7 @@ func TestSetAssetTypes(t *testing.T) {
}
exch.AssetTypes = ""
err = cfg.UpdateExchangeConfig(exch)
err = cfg.UpdateExchangeConfig(&exch)
if err != nil {
t.Fatalf("Test failed. TestSetAssetTypes update config failed. Error %s", err)
}
@@ -316,7 +321,7 @@ func TestSetCurrencyPairFormat(t *testing.T) {
t.Fatal("Test failed. TestSetCurrencyPairFormat returned nil error for a non-existent exchange")
}
b.Name = "ANX"
b.Name = defaultTestExchange
err = b.SetCurrencyPairFormat()
if err != nil {
t.Fatalf("Test failed. TestSetCurrencyPairFormat. Error %s", err)
@@ -329,7 +334,7 @@ func TestSetCurrencyPairFormat(t *testing.T) {
exch.ConfigCurrencyPairFormat = nil
exch.RequestCurrencyPairFormat = nil
err = cfg.UpdateExchangeConfig(exch)
err = cfg.UpdateExchangeConfig(&exch)
if err != nil {
t.Fatalf("Test failed. TestSetCurrencyPairFormat update config failed. Error %s", err)
}
@@ -349,13 +354,13 @@ func TestSetCurrencyPairFormat(t *testing.T) {
}
if b.ConfigCurrencyPairFormat.Delimiter != "" &&
b.ConfigCurrencyPairFormat.Index != "BTC" &&
b.ConfigCurrencyPairFormat.Index != symbol.BTC &&
b.ConfigCurrencyPairFormat.Uppercase {
t.Fatal("Test failed. TestSetCurrencyPairFormat ConfigCurrencyPairFormat values are incorrect")
}
if b.RequestCurrencyPairFormat.Delimiter != "" &&
b.RequestCurrencyPairFormat.Index != "BTC" &&
b.RequestCurrencyPairFormat.Index != symbol.BTC &&
b.RequestCurrencyPairFormat.Uppercase {
t.Fatal("Test failed. TestSetCurrencyPairFormat RequestCurrencyPairFormat values are incorrect")
}
@@ -393,7 +398,7 @@ func TestGetEnabledCurrencies(t *testing.T) {
Name: "TESTNAME",
}
b.EnabledPairs = []string{"BTC-USD"}
b.EnabledPairs = []string{defaultTestCurrencyPair}
format := config.CurrencyPairFormatConfig{
Delimiter: "-",
Index: "",
@@ -402,29 +407,29 @@ func TestGetEnabledCurrencies(t *testing.T) {
b.RequestCurrencyPairFormat = format
b.ConfigCurrencyPairFormat = format
c := b.GetEnabledCurrencies()
if c[0].Pair().String() != "BTC-USD" {
if c[0].Pair().String() != defaultTestCurrencyPair {
t.Error("Test Failed - Exchange GetAvailableCurrencies() incorrect string")
}
format.Delimiter = "~"
b.RequestCurrencyPairFormat = format
c = b.GetEnabledCurrencies()
if c[0].Pair().String() != "BTC-USD" {
if c[0].Pair().String() != defaultTestCurrencyPair {
t.Error("Test Failed - Exchange GetAvailableCurrencies() incorrect string")
}
format.Delimiter = ""
b.ConfigCurrencyPairFormat = format
c = b.GetEnabledCurrencies()
if c[0].Pair().String() != "BTC-USD" {
if c[0].Pair().String() != defaultTestCurrencyPair {
t.Error("Test Failed - Exchange GetAvailableCurrencies() incorrect string")
}
b.EnabledPairs = []string{"BTCDOGE"}
format.Index = "BTC"
format.Index = symbol.BTC
b.ConfigCurrencyPairFormat = format
c = b.GetEnabledCurrencies()
if c[0].FirstCurrency.String() != "BTC" && c[0].SecondCurrency.String() != "DOGE" {
if c[0].FirstCurrency.String() != symbol.BTC && c[0].SecondCurrency.String() != "DOGE" {
t.Error("Test Failed - Exchange GetAvailableCurrencies() incorrect string")
}
@@ -432,23 +437,23 @@ func TestGetEnabledCurrencies(t *testing.T) {
b.RequestCurrencyPairFormat.Delimiter = ""
b.ConfigCurrencyPairFormat.Delimiter = "_"
c = b.GetEnabledCurrencies()
if c[0].FirstCurrency.String() != "BTC" && c[0].SecondCurrency.String() != "USD" {
if c[0].FirstCurrency.String() != symbol.BTC && c[0].SecondCurrency.String() != symbol.USD {
t.Error("Test Failed - Exchange GetAvailableCurrencies() incorrect string")
}
b.EnabledPairs = []string{"BTCDOGE"}
b.RequestCurrencyPairFormat.Delimiter = ""
b.ConfigCurrencyPairFormat.Delimiter = ""
b.ConfigCurrencyPairFormat.Index = "BTC"
b.ConfigCurrencyPairFormat.Index = symbol.BTC
c = b.GetEnabledCurrencies()
if c[0].FirstCurrency.String() != "BTC" && c[0].SecondCurrency.String() != "DOGE" {
if c[0].FirstCurrency.String() != symbol.BTC && c[0].SecondCurrency.String() != "DOGE" {
t.Error("Test Failed - Exchange GetAvailableCurrencies() incorrect string")
}
b.EnabledPairs = []string{"BTCUSD"}
b.ConfigCurrencyPairFormat.Index = ""
c = b.GetEnabledCurrencies()
if c[0].FirstCurrency.String() != "BTC" && c[0].SecondCurrency.String() != "USD" {
if c[0].FirstCurrency.String() != symbol.BTC && c[0].SecondCurrency.String() != symbol.USD {
t.Error("Test Failed - Exchange GetAvailableCurrencies() incorrect string")
}
}
@@ -458,7 +463,7 @@ func TestGetAvailableCurrencies(t *testing.T) {
Name: "TESTNAME",
}
b.AvailablePairs = []string{"BTC-USD"}
b.AvailablePairs = []string{defaultTestCurrencyPair}
format := config.CurrencyPairFormatConfig{
Delimiter: "-",
Index: "",
@@ -467,29 +472,29 @@ func TestGetAvailableCurrencies(t *testing.T) {
b.RequestCurrencyPairFormat = format
b.ConfigCurrencyPairFormat = format
c := b.GetAvailableCurrencies()
if c[0].Pair().String() != "BTC-USD" {
if c[0].Pair().String() != defaultTestCurrencyPair {
t.Error("Test Failed - Exchange GetAvailableCurrencies() incorrect string")
}
format.Delimiter = "~"
b.RequestCurrencyPairFormat = format
c = b.GetAvailableCurrencies()
if c[0].Pair().String() != "BTC-USD" {
if c[0].Pair().String() != defaultTestCurrencyPair {
t.Error("Test Failed - Exchange GetAvailableCurrencies() incorrect string")
}
format.Delimiter = ""
b.ConfigCurrencyPairFormat = format
c = b.GetAvailableCurrencies()
if c[0].Pair().String() != "BTC-USD" {
if c[0].Pair().String() != defaultTestCurrencyPair {
t.Error("Test Failed - Exchange GetAvailableCurrencies() incorrect string")
}
b.AvailablePairs = []string{"BTCDOGE"}
format.Index = "BTC"
format.Index = symbol.BTC
b.ConfigCurrencyPairFormat = format
c = b.GetAvailableCurrencies()
if c[0].FirstCurrency.String() != "BTC" && c[0].SecondCurrency.String() != "DOGE" {
if c[0].FirstCurrency.String() != symbol.BTC && c[0].SecondCurrency.String() != "DOGE" {
t.Error("Test Failed - Exchange GetAvailableCurrencies() incorrect string")
}
@@ -497,23 +502,23 @@ func TestGetAvailableCurrencies(t *testing.T) {
b.RequestCurrencyPairFormat.Delimiter = ""
b.ConfigCurrencyPairFormat.Delimiter = "_"
c = b.GetAvailableCurrencies()
if c[0].FirstCurrency.String() != "BTC" && c[0].SecondCurrency.String() != "USD" {
if c[0].FirstCurrency.String() != symbol.BTC && c[0].SecondCurrency.String() != symbol.USD {
t.Error("Test Failed - Exchange GetAvailableCurrencies() incorrect string")
}
b.AvailablePairs = []string{"BTCDOGE"}
b.RequestCurrencyPairFormat.Delimiter = ""
b.ConfigCurrencyPairFormat.Delimiter = ""
b.ConfigCurrencyPairFormat.Index = "BTC"
b.ConfigCurrencyPairFormat.Index = symbol.BTC
c = b.GetAvailableCurrencies()
if c[0].FirstCurrency.String() != "BTC" && c[0].SecondCurrency.String() != "DOGE" {
if c[0].FirstCurrency.String() != symbol.BTC && c[0].SecondCurrency.String() != "DOGE" {
t.Error("Test Failed - Exchange GetAvailableCurrencies() incorrect string")
}
b.AvailablePairs = []string{"BTCUSD"}
b.ConfigCurrencyPairFormat.Index = ""
c = b.GetAvailableCurrencies()
if c[0].FirstCurrency.String() != "BTC" && c[0].SecondCurrency.String() != "USD" {
if c[0].FirstCurrency.String() != symbol.BTC && c[0].SecondCurrency.String() != symbol.USD {
t.Error("Test Failed - Exchange GetAvailableCurrencies() incorrect string")
}
}
@@ -523,8 +528,8 @@ func TestSupportsCurrency(t *testing.T) {
Name: "TESTNAME",
}
b.AvailablePairs = []string{"BTC-USD", "ETH-USD"}
b.EnabledPairs = []string{"BTC-USD"}
b.AvailablePairs = []string{defaultTestCurrencyPair, "ETH-USD"}
b.EnabledPairs = []string{defaultTestCurrencyPair}
format := config.CurrencyPairFormatConfig{
Delimiter: "-",
@@ -534,11 +539,11 @@ func TestSupportsCurrency(t *testing.T) {
b.RequestCurrencyPairFormat = format
b.ConfigCurrencyPairFormat = format
if !b.SupportsCurrency(pair.NewCurrencyPair("BTC", "USD"), true) {
if !b.SupportsCurrency(pair.NewCurrencyPair(symbol.BTC, symbol.USD), true) {
t.Error("Test Failed - Exchange SupportsCurrency() incorrect value")
}
if !b.SupportsCurrency(pair.NewCurrencyPair("ETH", "USD"), false) {
if !b.SupportsCurrency(pair.NewCurrencyPair("ETH", symbol.USD), false) {
t.Error("Test Failed - Exchange SupportsCurrency() incorrect value")
}
@@ -585,9 +590,10 @@ func TestGetAndFormatExchangeCurrencies(t *testing.T) {
t.Fatalf("Failed to load config file. Error: %s", err)
}
var pairs []pair.CurrencyPair
pairs = append(pairs, pair.NewCurrencyPairDelimiter("BTC_USD", "_"))
pairs = append(pairs, pair.NewCurrencyPairDelimiter("LTC_BTC", "_"))
var pairs = []pair.CurrencyPair{
pair.NewCurrencyPairDelimiter("BTC_USD", "_"),
pair.NewCurrencyPairDelimiter("LTC_BTC", "_"),
}
actual, err := GetAndFormatExchangeCurrencies("Yobit", pairs)
if err != nil {
@@ -613,9 +619,9 @@ func TestFormatExchangeCurrency(t *testing.T) {
t.Fatalf("Failed to load config file. Error: %s", err)
}
pair := pair.NewCurrencyPair("BTC", "USD")
expected := "BTC-USD"
actual := FormatExchangeCurrency("CoinbasePro", pair)
p := pair.NewCurrencyPair(symbol.BTC, symbol.USD)
expected := defaultTestCurrencyPair
actual := FormatExchangeCurrency("CoinbasePro", p)
if actual.String() != expected {
t.Errorf("Test failed - Exchange TestFormatExchangeCurrency %s != %s",
@@ -630,8 +636,8 @@ func TestFormatCurrency(t *testing.T) {
t.Fatalf("Failed to load config file. Error: %s", err)
}
currency := pair.NewCurrencyPair("btc", "usd")
expected := "BTC-USD"
currency := pair.NewCurrencyPair(symbol.BTC, symbol.USD)
expected := defaultTestCurrencyPair
actual := FormatCurrency(currency).String()
if actual != expected {
t.Errorf("Test failed - Exchange TestFormatCurrency %s != %s",
@@ -699,12 +705,12 @@ func TestSetCurrencies(t *testing.T) {
t.Fatal("Test failed. TestSetCurrencies returned nil error on non-existent exchange")
}
anxCfg, err := cfg.GetExchangeConfig("ANX")
anxCfg, err := cfg.GetExchangeConfig(defaultTestExchange)
if err != nil {
t.Fatal("Test failed. TestSetCurrencies failed to load config")
}
UAC.Name = "ANX"
UAC.Name = defaultTestExchange
UAC.ConfigCurrencyPairFormat.Delimiter = anxCfg.ConfigCurrencyPairFormat.Delimiter
UAC.SetCurrencies([]pair.CurrencyPair{newPair}, true)
if !pair.Contains(UAC.GetEnabledCurrencies(), newPair, true) {
@@ -729,8 +735,8 @@ func TestUpdateCurrencies(t *testing.T) {
t.Fatal("Test failed. TestUpdateEnabledCurrencies failed to load config")
}
UAC := Base{Name: "ANX"}
exchangeProducts := []string{"ltc", "btc", "usd", "aud", ""}
UAC := Base{Name: defaultTestExchange}
exchangeProducts := []string{"ltc", symbol.BTC, symbol.USD, "aud", ""}
// Test updating exchange products for an exchange which doesn't exist
UAC.Name = "Blah"
@@ -740,27 +746,27 @@ func TestUpdateCurrencies(t *testing.T) {
}
// Test updating exchange products
UAC.Name = "ANX"
UAC.Name = defaultTestExchange
err = UAC.UpdateCurrencies(exchangeProducts, true, false)
if err != nil {
t.Errorf("Test Failed - Exchange TestUpdateCurrencies error: %s", err)
}
// Test updating the same new products, diff should be 0
UAC.Name = "ANX"
UAC.Name = defaultTestExchange
err = UAC.UpdateCurrencies(exchangeProducts, true, false)
if err != nil {
t.Errorf("Test Failed - Exchange TestUpdateCurrencies error: %s", err)
}
// Test force updating to only one product
exchangeProducts = []string{"btc"}
exchangeProducts = []string{symbol.BTC}
err = UAC.UpdateCurrencies(exchangeProducts, true, true)
if err != nil {
t.Errorf("Test Failed - Forced Exchange TestUpdateCurrencies error: %s", err)
}
exchangeProducts = []string{"ltc", "btc", "usd", "aud"}
exchangeProducts = []string{"ltc", symbol.BTC, symbol.USD, "aud"}
// Test updating exchange products for an exchange which doesn't exist
UAC.Name = "Blah"
err = UAC.UpdateCurrencies(exchangeProducts, false, false)
@@ -769,21 +775,21 @@ func TestUpdateCurrencies(t *testing.T) {
}
// Test updating exchange products
UAC.Name = "ANX"
UAC.Name = defaultTestExchange
err = UAC.UpdateCurrencies(exchangeProducts, false, false)
if err != nil {
t.Errorf("Test Failed - Exchange UpdateCurrencies() error: %s", err)
}
// Test updating the same new products, diff should be 0
UAC.Name = "ANX"
UAC.Name = defaultTestExchange
err = UAC.UpdateCurrencies(exchangeProducts, false, false)
if err != nil {
t.Errorf("Test Failed - Exchange UpdateCurrencies() error: %s", err)
}
// Test force updating to only one product
exchangeProducts = []string{"btc"}
exchangeProducts = []string{symbol.BTC}
err = UAC.UpdateCurrencies(exchangeProducts, false, true)
if err != nil {
t.Errorf("Test Failed - Forced Exchange UpdateCurrencies() error: %s", err)
@@ -848,7 +854,7 @@ func TestAPIURL(t *testing.T) {
}
func TestSupportsWithdrawPermissions(t *testing.T) {
UAC := Base{Name: "ANX"}
UAC := Base{Name: defaultTestExchange}
UAC.APIWithdrawPermissions = AutoWithdrawCrypto | AutoWithdrawCryptoWithAPIPermission
withdrawPermissions := UAC.SupportsWithdrawPermissions(AutoWithdrawCrypto)
@@ -884,7 +890,7 @@ func TestFormatWithdrawPermissions(t *testing.T) {
t.Fatal("Test failed. TestUpdateEnabledCurrencies failed to load config")
}
UAC := Base{Name: "ANX"}
UAC := Base{Name: defaultTestExchange}
UAC.APIWithdrawPermissions = AutoWithdrawCrypto |
AutoWithdrawCryptoWithAPIPermission |
AutoWithdrawCryptoWithSetup |
@@ -933,14 +939,14 @@ func TestOrderTypes(t *testing.T) {
}
func TestFilterOrdersByType(t *testing.T) {
var orders []OrderDetail
orders = append(orders, OrderDetail{
OrderType: ImmediateOrCancelOrderType,
})
orders = append(orders, OrderDetail{
OrderType: LimitOrderType,
})
var orders = []OrderDetail{
{
OrderType: ImmediateOrCancelOrderType,
},
{
OrderType: LimitOrderType,
},
}
FilterOrdersByType(&orders, AnyOrderType)
if len(orders) != 2 {
@@ -959,15 +965,15 @@ func TestFilterOrdersByType(t *testing.T) {
}
func TestFilterOrdersBySide(t *testing.T) {
var orders []OrderDetail
orders = append(orders, OrderDetail{
OrderSide: BuyOrderSide,
})
orders = append(orders, OrderDetail{
OrderSide: SellOrderSide,
})
orders = append(orders, OrderDetail{})
var orders = []OrderDetail{
{
OrderSide: BuyOrderSide,
},
{
OrderSide: SellOrderSide,
},
{},
}
FilterOrdersBySide(&orders, AnyOrderSide)
if len(orders) != 3 {
@@ -986,17 +992,17 @@ func TestFilterOrdersBySide(t *testing.T) {
}
func TestFilterOrdersByTickRange(t *testing.T) {
var orders []OrderDetail
orders = append(orders, OrderDetail{
OrderDate: time.Unix(100, 0),
})
orders = append(orders, OrderDetail{
OrderDate: time.Unix(110, 0),
})
orders = append(orders, OrderDetail{
OrderDate: time.Unix(111, 0),
})
var orders = []OrderDetail{
{
OrderDate: time.Unix(100, 0),
},
{
OrderDate: time.Unix(110, 0),
},
{
OrderDate: time.Unix(111, 0),
},
}
FilterOrdersByTickRange(&orders, time.Unix(0, 0), time.Unix(0, 0))
if len(orders) != 3 {
@@ -1020,17 +1026,17 @@ func TestFilterOrdersByTickRange(t *testing.T) {
}
func TestFilterOrdersByCurrencies(t *testing.T) {
var orders []OrderDetail
orders = append(orders, OrderDetail{
CurrencyPair: pair.NewCurrencyPair(symbol.BTC, symbol.USD),
})
orders = append(orders, OrderDetail{
CurrencyPair: pair.NewCurrencyPair(symbol.LTC, symbol.EUR),
})
orders = append(orders, OrderDetail{
CurrencyPair: pair.NewCurrencyPair(symbol.DOGE, symbol.RUB),
})
var orders = []OrderDetail{
{
CurrencyPair: pair.NewCurrencyPair(symbol.BTC, symbol.USD),
},
{
CurrencyPair: pair.NewCurrencyPair(symbol.LTC, symbol.EUR),
},
{
CurrencyPair: pair.NewCurrencyPair(symbol.DOGE, symbol.RUB),
},
}
currencies := []pair.CurrencyPair{pair.NewCurrencyPair(symbol.BTC, symbol.USD), pair.NewCurrencyPair(symbol.LTC, symbol.EUR), pair.NewCurrencyPair(symbol.DOGE, symbol.RUB)}
FilterOrdersByCurrencies(&orders, currencies)

View File

@@ -246,12 +246,12 @@ func (w *Websocket) Shutdown() error {
}
// SetWebsocketURL sets websocket URL
func (w *Websocket) SetWebsocketURL(URL string) {
if URL == "" || URL == config.WebsocketURLNonDefaultMessage {
func (w *Websocket) SetWebsocketURL(websocketURL string) {
if websocketURL == "" || websocketURL == config.WebsocketURLNonDefaultMessage {
w.runningURL = w.defaultURL
return
}
w.runningURL = URL
w.runningURL = websocketURL
}
// GetWebsocketURL returns the running websocket URL
@@ -293,12 +293,12 @@ func (w *Websocket) IsEnabled() bool {
}
// SetProxyAddress sets websocket proxy address
func (w *Websocket) SetProxyAddress(URL string) error {
if w.proxyAddr == URL {
func (w *Websocket) SetProxyAddress(proxyAddr string) error {
if w.proxyAddr == proxyAddr {
return errors.New("exchange_websocket.go error - Setting proxy address - same address")
}
w.proxyAddr = URL
w.proxyAddr = proxyAddr
if !w.init && w.enabled {
if w.connected {
@@ -401,7 +401,7 @@ func (w *WebsocketOrderbookLocal) Update(bidTargets, askTargets []orderbook.Item
if orderbookAddress.Bids[y].Price == bidTargets[x].Price {
if bidTargets[x].Amount == 0 {
// Delete
orderbookAddress.Asks = append(orderbookAddress.Bids[:y],
orderbookAddress.Bids = append(orderbookAddress.Bids[:y],
orderbookAddress.Bids[y+1:]...)
return
}

View File

@@ -119,9 +119,9 @@ func (e *EXMO) GetTrades(symbol string) (map[string][]Trades, error) {
v := url.Values{}
v.Set("pair", symbol)
result := make(map[string][]Trades)
url := fmt.Sprintf("%s/v%s/%s", e.APIUrl, exmoAPIVersion, exmoTrades)
urlPath := fmt.Sprintf("%s/v%s/%s", e.APIUrl, exmoAPIVersion, exmoTrades)
return result, e.SendHTTPRequest(common.EncodeURLValues(url, v), &result)
return result, e.SendHTTPRequest(common.EncodeURLValues(urlPath, v), &result)
}
// GetOrderbook returns the orderbook for a symbol or symbols
@@ -129,9 +129,9 @@ func (e *EXMO) GetOrderbook(symbol string) (map[string]Orderbook, error) {
v := url.Values{}
v.Set("pair", symbol)
result := make(map[string]Orderbook)
url := fmt.Sprintf("%s/v%s/%s", e.APIUrl, exmoAPIVersion, exmoOrderbook)
urlPath := fmt.Sprintf("%s/v%s/%s", e.APIUrl, exmoAPIVersion, exmoOrderbook)
return result, e.SendHTTPRequest(common.EncodeURLValues(url, v), &result)
return result, e.SendHTTPRequest(common.EncodeURLValues(urlPath, v), &result)
}
// GetTicker returns the ticker for a symbol or symbols
@@ -139,25 +139,24 @@ func (e *EXMO) GetTicker(symbol string) (map[string]Ticker, error) {
v := url.Values{}
v.Set("pair", symbol)
result := make(map[string]Ticker)
url := fmt.Sprintf("%s/v%s/%s", e.APIUrl, exmoAPIVersion, exmoTicker)
urlPath := fmt.Sprintf("%s/v%s/%s", e.APIUrl, exmoAPIVersion, exmoTicker)
return result, e.SendHTTPRequest(common.EncodeURLValues(url, v), &result)
return result, e.SendHTTPRequest(common.EncodeURLValues(urlPath, v), &result)
}
// GetPairSettings returns the pair settings for a symbol or symbols
func (e *EXMO) GetPairSettings() (map[string]PairSettings, error) {
result := make(map[string]PairSettings)
url := fmt.Sprintf("%s/v%s/%s", e.APIUrl, exmoAPIVersion, exmoPairSettings)
urlPath := fmt.Sprintf("%s/v%s/%s", e.APIUrl, exmoAPIVersion, exmoPairSettings)
return result, e.SendHTTPRequest(url, &result)
return result, e.SendHTTPRequest(urlPath, &result)
}
// GetCurrency returns a list of currencies
func (e *EXMO) GetCurrency() ([]string, error) {
result := []string{}
url := fmt.Sprintf("%s/v%s/%s", e.APIUrl, exmoAPIVersion, exmoCurrency)
return result, e.SendHTTPRequest(url, &result)
urlPath := fmt.Sprintf("%s/v%s/%s", e.APIUrl, exmoAPIVersion, exmoCurrency)
return result, e.SendHTTPRequest(urlPath, &result)
}
// GetUserInfo returns the user info
@@ -445,11 +444,12 @@ func getInternationalBankWithdrawalFee(currency string, amount float64, bankTran
switch bankTransactionType {
case exchange.WireTransfer:
if currency == symbol.RUB {
switch currency {
case symbol.RUB:
fee = 3200
} else if currency == symbol.PLN {
case symbol.PLN:
fee = 125
} else if currency == symbol.TRY {
case symbol.TRY:
fee = 0
}
case exchange.PerfectMoney:
@@ -513,11 +513,12 @@ func getInternationalBankDepositFee(currency string, amount float64, bankTransac
var fee float64
switch bankTransactionType {
case exchange.WireTransfer:
if currency == symbol.RUB {
switch currency {
case symbol.RUB:
fee = 1600
} else if currency == symbol.PLN {
case symbol.PLN:
fee = 30
} else if currency == symbol.TRY {
case symbol.TRY:
fee = 0
}
case exchange.Neteller:

View File

@@ -188,16 +188,17 @@ func (e *EXMO) GetExchangeHistory(p pair.CurrencyPair, assetType string) ([]exch
func (e *EXMO) SubmitOrder(p pair.CurrencyPair, side exchange.OrderSide, orderType exchange.OrderType, amount, price float64, _ string) (exchange.SubmitOrderResponse, error) {
var submitOrderResponse exchange.SubmitOrderResponse
var oT string
if orderType == exchange.LimitOrderType {
return submitOrderResponse, errors.New("Unsupported order type")
} else if orderType == exchange.MarketOrderType {
if side == exchange.BuyOrderSide {
oT = "market_buy"
} else {
switch orderType {
case exchange.LimitOrderType:
return submitOrderResponse, errors.New("unsupported order type")
case exchange.MarketOrderType:
oT = "market_buy"
if side == exchange.SellOrderSide {
oT = "market_sell"
}
} else {
return submitOrderResponse, errors.New("Unsupported order type")
default:
return submitOrderResponse, errors.New("unsupported order type")
}
response, err := e.CreateOrder(p.Pair().String(), oT, price, amount)
@@ -332,8 +333,8 @@ func (e *EXMO) GetActiveOrders(getOrdersRequest exchange.GetOrdersRequest) ([]ex
// GetOrderHistory retrieves account order information
// Can Limit response to specific order status
func (e *EXMO) GetOrderHistory(getOrdersRequest exchange.GetOrdersRequest) ([]exchange.OrderDetail, error) {
if len(getOrdersRequest.Currencies) <= 0 {
return nil, errors.New("Currency must be supplied")
if len(getOrdersRequest.Currencies) == 0 {
return nil, errors.New("currency must be supplied")
}
var allTrades []UserTrades

View File

@@ -131,9 +131,9 @@ func (g *Gateio) Setup(exch config.ExchangeConfig) {
func (g *Gateio) GetSymbols() ([]string, error) {
var result []string
url := fmt.Sprintf("%s/%s/%s", g.APIUrlSecondary, gateioAPIVersion, gateioSymbol)
urlPath := fmt.Sprintf("%s/%s/%s", g.APIUrlSecondary, gateioAPIVersion, gateioSymbol)
err := g.SendHTTPRequest(url, &result)
err := g.SendHTTPRequest(urlPath, &result)
if err != nil {
return nil, nil
}
@@ -148,11 +148,11 @@ func (g *Gateio) GetMarketInfo() (MarketInfoResponse, error) {
Pairs []interface{} `json:"pairs"`
}
url := fmt.Sprintf("%s/%s/%s", g.APIUrlSecondary, gateioAPIVersion, gateioMarketInfo)
urlPath := fmt.Sprintf("%s/%s/%s", g.APIUrlSecondary, gateioAPIVersion, gateioMarketInfo)
var res response
var result MarketInfoResponse
err := g.SendHTTPRequest(url, &res)
err := g.SendHTTPRequest(urlPath, &res)
if err != nil {
return result, err
}
@@ -189,17 +189,17 @@ func (g *Gateio) GetLatestSpotPrice(symbol string) (float64, error) {
// GetTicker returns a ticker for the supplied symbol
// updated every 10 seconds
func (g *Gateio) GetTicker(symbol string) (TickerResponse, error) {
url := fmt.Sprintf("%s/%s/%s/%s", g.APIUrlSecondary, gateioAPIVersion, gateioTicker, symbol)
urlPath := fmt.Sprintf("%s/%s/%s/%s", g.APIUrlSecondary, gateioAPIVersion, gateioTicker, symbol)
var res TickerResponse
return res, g.SendHTTPRequest(url, &res)
return res, g.SendHTTPRequest(urlPath, &res)
}
// GetTickers returns tickers for all symbols
func (g *Gateio) GetTickers() (map[string]TickerResponse, error) {
url := fmt.Sprintf("%s/%s/%s", g.APIUrlSecondary, gateioAPIVersion, gateioTickers)
urlPath := fmt.Sprintf("%s/%s/%s", g.APIUrlSecondary, gateioAPIVersion, gateioTickers)
resp := make(map[string]TickerResponse)
err := g.SendHTTPRequest(url, &resp)
err := g.SendHTTPRequest(urlPath, &resp)
if err != nil {
return nil, err
}
@@ -208,10 +208,10 @@ func (g *Gateio) GetTickers() (map[string]TickerResponse, error) {
// GetOrderbook returns the orderbook data for a suppled symbol
func (g *Gateio) GetOrderbook(symbol string) (Orderbook, error) {
url := fmt.Sprintf("%s/%s/%s/%s", g.APIUrlSecondary, gateioAPIVersion, gateioOrderbook, symbol)
urlPath := fmt.Sprintf("%s/%s/%s/%s", g.APIUrlSecondary, gateioAPIVersion, gateioOrderbook, symbol)
var resp OrderbookResponse
err := g.SendHTTPRequest(url, &resp)
err := g.SendHTTPRequest(urlPath, &resp)
if err != nil {
return Orderbook{}, err
}
@@ -270,7 +270,7 @@ func (g *Gateio) GetOrderbook(symbol string) (Orderbook, error) {
// GetSpotKline returns kline data for the most recent time period
func (g *Gateio) GetSpotKline(arg KlinesRequestParams) ([]*KLineResponse, error) {
url := fmt.Sprintf("%s/%s/%s/%s?group_sec=%d&range_hour=%d",
urlPath := fmt.Sprintf("%s/%s/%s/%s?group_sec=%d&range_hour=%d",
g.APIUrlSecondary,
gateioAPIVersion,
gateioKline,
@@ -279,7 +279,7 @@ func (g *Gateio) GetSpotKline(arg KlinesRequestParams) ([]*KLineResponse, error)
arg.HourSize)
var rawKlines map[string]interface{}
err := g.SendHTTPRequest(url, &rawKlines)
err := g.SendHTTPRequest(urlPath, &rawKlines)
if err != nil {
return nil, err
}
@@ -357,8 +357,8 @@ func (g *Gateio) SpotNewOrder(arg SpotNewOrderRequestParams) (SpotNewOrderRespon
strconv.FormatFloat(arg.Amount, 'f', -1, 64),
)
strRequestURL := fmt.Sprintf("%s/%s", gateioOrder, arg.Type)
return result, g.SendAuthenticatedHTTPRequest(http.MethodPost, strRequestURL, params, &result)
urlPath := fmt.Sprintf("%s/%s", gateioOrder, arg.Type)
return result, g.SendAuthenticatedHTTPRequest(http.MethodPost, urlPath, params, &result)
}
// CancelExistingOrder cancels an order given the supplied orderID and symbol
@@ -472,11 +472,11 @@ func (g *Gateio) SendAuthenticatedHTTPRequest(method, endpoint, param string, re
hmac := common.GetHMAC(common.HashSHA512, []byte(param), []byte(g.APISecret))
headers["sign"] = common.HexEncodeToString(hmac)
url := fmt.Sprintf("%s/%s/%s", g.APIUrl, gateioAPIVersion, endpoint)
urlPath := fmt.Sprintf("%s/%s/%s", g.APIUrl, gateioAPIVersion, endpoint)
var intermidiary json.RawMessage
err := g.SendPayload(method, url, headers, strings.NewReader(param), &intermidiary, true, g.Verbose)
err := g.SendPayload(method, urlPath, headers, strings.NewReader(param), &intermidiary, true, g.Verbose)
if err != nil {
return err
}
@@ -489,7 +489,8 @@ func (g *Gateio) SendAuthenticatedHTTPRequest(method, endpoint, param string, re
if err := common.JSONDecode(intermidiary, &errCap); err == nil {
if !errCap.Result {
return fmt.Errorf("GateIO auth request error, code: %d message: %s",
return fmt.Errorf("%s auth request error, code: %d message: %s",
g.Name,
errCap.Code,
errCap.Message)
}
@@ -514,7 +515,7 @@ func (g *Gateio) GetFee(feeBuilder exchange.FeeBuilder) (fee float64, err error)
}
}
if feeForPair == 0 {
return 0, fmt.Errorf("Currency: '%s' failed to find fee data", currencyPair)
return 0, fmt.Errorf("currency '%s' failed to find fee data", currencyPair)
}
fee = calculateTradingFee(feeForPair, feeBuilder.PurchasePrice, feeBuilder.Amount)
case exchange.CryptocurrencyWithdrawalFee:

View File

@@ -305,7 +305,7 @@ func (g *Gateio) WsHandleData() {
}
open, _ := strconv.ParseFloat(data[1].(string), 64)
close, _ := strconv.ParseFloat(data[2].(string), 64)
closePrice, _ := strconv.ParseFloat(data[2].(string), 64)
high, _ := strconv.ParseFloat(data[3].(string), 64)
low, _ := strconv.ParseFloat(data[4].(string), 64)
volume, _ := strconv.ParseFloat(data[5].(string), 64)
@@ -316,7 +316,7 @@ func (g *Gateio) WsHandleData() {
AssetType: "SPOT",
Exchange: g.GetName(),
OpenPrice: open,
ClosePrice: close,
ClosePrice: closePrice,
HighPrice: high,
LowPrice: low,
Volume: volume,

View File

@@ -247,7 +247,7 @@ func (g *Gateio) CancelAllOrders(_ exchange.OrderCancellation) (exchange.CancelA
return cancelAllOrdersResponse, err
}
var uniqueSymbols map[string]string
uniqueSymbols := make(map[string]string)
for _, openOrder := range openOrders.Orders {
uniqueSymbols[openOrder.CurrencyPair] = openOrder.CurrencyPair
}
@@ -280,8 +280,11 @@ func (g *Gateio) GetDepositAddress(cryptocurrency pair.CurrencyItem, _ string) (
if addr == gateioGenerateAddress {
time.Sleep(10 * time.Second)
addr, err = g.GetCryptoDepositAddress(cryptocurrency.String())
if err != nil {
return "", err
}
if addr == gateioGenerateAddress {
return "", errors.New("address not generated in time")
return "", errors.New("new deposit address is being generated, please retry again shortly")
}
return addr, nil
}

View File

@@ -300,15 +300,15 @@ func (g *Gemini) NewOrder(symbol string, amount, price float64, side, orderType
return 0, err
}
request := make(map[string]interface{})
request["symbol"] = symbol
request["amount"] = strconv.FormatFloat(amount, 'f', -1, 64)
request["price"] = strconv.FormatFloat(price, 'f', -1, 64)
request["side"] = side
request["type"] = orderType
req := make(map[string]interface{})
req["symbol"] = symbol
req["amount"] = strconv.FormatFloat(amount, 'f', -1, 64)
req["price"] = strconv.FormatFloat(price, 'f', -1, 64)
req["side"] = side
req["type"] = orderType
response := Order{}
err := g.SendAuthenticatedHTTPRequest(http.MethodPost, geminiOrderNew, request, &response)
err := g.SendAuthenticatedHTTPRequest(http.MethodPost, geminiOrderNew, req, &response)
if err != nil {
return 0, err
}
@@ -317,12 +317,12 @@ func (g *Gemini) NewOrder(symbol string, amount, price float64, side, orderType
// CancelExistingOrder will cancel an order. If the order is already canceled, the
// message will succeed but have no effect.
func (g *Gemini) CancelExistingOrder(OrderID int64) (Order, error) {
request := make(map[string]interface{})
request["order_id"] = OrderID
func (g *Gemini) CancelExistingOrder(orderID int64) (Order, error) {
req := make(map[string]interface{})
req["order_id"] = orderID
response := Order{}
err := g.SendAuthenticatedHTTPRequest(http.MethodPost, geminiOrderCancel, request, &response)
err := g.SendAuthenticatedHTTPRequest(http.MethodPost, geminiOrderCancel, req, &response)
if err != nil {
return Order{}, err
}
@@ -337,10 +337,10 @@ func (g *Gemini) CancelExistingOrder(OrderID int64) (Order, error) {
// sessions owned by this account, including interactive orders placed through
// the UI. If sessions = true will only cancel the order that is called on this
// session asssociated with the APIKEY
func (g *Gemini) CancelExistingOrders(CancelBySession bool) (OrderResult, error) {
func (g *Gemini) CancelExistingOrders(cancelBySession bool) (OrderResult, error) {
response := OrderResult{}
path := geminiOrderCancelAll
if CancelBySession {
if cancelBySession {
path = geminiOrderCancelSession
}
@@ -356,12 +356,12 @@ func (g *Gemini) CancelExistingOrders(CancelBySession bool) (OrderResult, error)
// GetOrderStatus returns the status for an order
func (g *Gemini) GetOrderStatus(orderID int64) (Order, error) {
request := make(map[string]interface{})
request["order_id"] = orderID
req := make(map[string]interface{})
req["order_id"] = orderID
response := Order{}
err := g.SendAuthenticatedHTTPRequest(http.MethodPost, geminiOrderStatus, request, &response)
err := g.SendAuthenticatedHTTPRequest(http.MethodPost, geminiOrderStatus, req, &response)
if err != nil {
return response, err
}
@@ -398,15 +398,15 @@ func (g *Gemini) GetOrders() ([]Order, error) {
// timestamp - [optional] Only return trades on or after this timestamp.
func (g *Gemini) GetTradeHistory(currencyPair string, timestamp int64) ([]TradeHistory, error) {
response := []TradeHistory{}
request := make(map[string]interface{})
request["symbol"] = currencyPair
req := make(map[string]interface{})
req["symbol"] = currencyPair
if timestamp != 0 {
request["timestamp"] = timestamp
req["timestamp"] = timestamp
}
return response,
g.SendAuthenticatedHTTPRequest(http.MethodPost, geminiMyTrades, request, &response)
g.SendAuthenticatedHTTPRequest(http.MethodPost, geminiMyTrades, req, &response)
}
// GetNotionalVolume returns the volume in price currency that has been traded across all pairs over a period of 30 days
@@ -436,13 +436,13 @@ func (g *Gemini) GetBalances() ([]Balance, error) {
// GetCryptoDepositAddress returns a deposit address
func (g *Gemini) GetCryptoDepositAddress(depositAddlabel, currency string) (DepositAddress, error) {
response := DepositAddress{}
request := make(map[string]interface{})
req := make(map[string]interface{})
if len(depositAddlabel) > 0 {
request["label"] = depositAddlabel
req["label"] = depositAddlabel
}
err := g.SendAuthenticatedHTTPRequest(http.MethodPost, geminiDeposit+"/"+currency+"/"+geminiNewAddress, request, &response)
err := g.SendAuthenticatedHTTPRequest(http.MethodPost, geminiDeposit+"/"+currency+"/"+geminiNewAddress, req, &response)
if err != nil {
return response, err
}
@@ -455,11 +455,11 @@ func (g *Gemini) GetCryptoDepositAddress(depositAddlabel, currency string) (Depo
// WithdrawCrypto withdraws crypto currency to a whitelisted address
func (g *Gemini) WithdrawCrypto(address, currency string, amount float64) (WithdrawalAddress, error) {
response := WithdrawalAddress{}
request := make(map[string]interface{})
request["address"] = address
request["amount"] = strconv.FormatFloat(amount, 'f', -1, 64)
req := make(map[string]interface{})
req["address"] = address
req["amount"] = strconv.FormatFloat(amount, 'f', -1, 64)
err := g.SendAuthenticatedHTTPRequest(http.MethodPost, geminiWithdraw+common.StringToLower(currency), request, &response)
err := g.SendAuthenticatedHTTPRequest(http.MethodPost, geminiWithdraw+common.StringToLower(currency), req, &response)
if err != nil {
return response, err
}
@@ -501,17 +501,17 @@ func (g *Gemini) SendAuthenticatedHTTPRequest(method, path string, params map[st
}
headers := make(map[string]string)
request := make(map[string]interface{})
request["request"] = fmt.Sprintf("/v%s/%s", geminiAPIVersion, path)
request["nonce"] = g.Nonce.GetValue(g.Name, false)
req := make(map[string]interface{})
req["request"] = fmt.Sprintf("/v%s/%s", geminiAPIVersion, path)
req["nonce"] = g.Nonce.GetValue(g.Name, false)
for key, value := range params {
request[key] = value
req[key] = value
}
PayloadJSON, err := common.JSONEncode(request)
PayloadJSON, err := common.JSONEncode(req)
if err != nil {
return errors.New("SendAuthenticatedHTTPRequest: Unable to JSON request")
return errors.New("sendAuthenticatedHTTPRequest: Unable to JSON request")
}
if g.Verbose {

View File

@@ -284,8 +284,8 @@ func (g *Gemini) GetActiveOrders(getOrdersRequest exchange.GetOrdersRequest) ([]
// GetOrderHistory retrieves account order information
// Can Limit response to specific order status
func (g *Gemini) GetOrderHistory(getOrdersRequest exchange.GetOrdersRequest) ([]exchange.OrderDetail, error) {
if len(getOrdersRequest.Currencies) <= 0 {
return nil, errors.New("Currency must be supplied")
if len(getOrdersRequest.Currencies) == 0 {
return nil, errors.New("currency must be supplied")
}
var trades []TradeHistory

View File

@@ -265,8 +265,8 @@ func (h *HitBTC) GetFeeByType(feeBuilder exchange.FeeBuilder) (float64, error) {
// GetActiveOrders retrieves any orders that are active/open
func (h *HitBTC) GetActiveOrders(getOrdersRequest exchange.GetOrdersRequest) ([]exchange.OrderDetail, error) {
if len(getOrdersRequest.Currencies) <= 0 {
return nil, errors.New("Currency must be supplied")
if len(getOrdersRequest.Currencies) == 0 {
return nil, errors.New("currency must be supplied")
}
var allOrders []OrderHistoryResponse
@@ -308,8 +308,8 @@ func (h *HitBTC) GetActiveOrders(getOrdersRequest exchange.GetOrdersRequest) ([]
// GetOrderHistory retrieves account order information
// Can Limit response to specific order status
func (h *HitBTC) GetOrderHistory(getOrdersRequest exchange.GetOrdersRequest) ([]exchange.OrderDetail, error) {
if len(getOrdersRequest.Currencies) <= 0 {
return nil, errors.New("Currency must be supplied")
if len(getOrdersRequest.Currencies) == 0 {
return nil, errors.New("currency must be supplied")
}
var allOrders []OrderHistoryResponse

View File

@@ -164,9 +164,9 @@ func (h *HUOBI) GetSpotKline(arg KlinesRequestParams) ([]KlineItem, error) {
}
var result response
url := fmt.Sprintf("%s/%s", h.APIUrl, huobiMarketHistoryKline)
urlPath := fmt.Sprintf("%s/%s", h.APIUrl, huobiMarketHistoryKline)
err := h.SendHTTPRequest(common.EncodeURLValues(url, vals), &result)
err := h.SendHTTPRequest(common.EncodeURLValues(urlPath, vals), &result)
if result.ErrorMessage != "" {
return nil, errors.New(result.ErrorMessage)
}
@@ -184,9 +184,9 @@ func (h *HUOBI) GetMarketDetailMerged(symbol string) (DetailMerged, error) {
}
var result response
url := fmt.Sprintf("%s/%s", h.APIUrl, huobiMarketDetailMerged)
urlPath := fmt.Sprintf("%s/%s", h.APIUrl, huobiMarketDetailMerged)
err := h.SendHTTPRequest(common.EncodeURLValues(url, vals), &result)
err := h.SendHTTPRequest(common.EncodeURLValues(urlPath, vals), &result)
if result.ErrorMessage != "" {
return result.Tick, errors.New(result.ErrorMessage)
}
@@ -208,9 +208,9 @@ func (h *HUOBI) GetDepth(obd OrderBookDataRequestParams) (Orderbook, error) {
}
var result response
url := fmt.Sprintf("%s/%s", h.APIUrl, huobiMarketDepth)
urlPath := fmt.Sprintf("%s/%s", h.APIUrl, huobiMarketDepth)
err := h.SendHTTPRequest(common.EncodeURLValues(url, vals), &result)
err := h.SendHTTPRequest(common.EncodeURLValues(urlPath, vals), &result)
if result.ErrorMessage != "" {
return result.Depth, errors.New(result.ErrorMessage)
}
@@ -230,9 +230,9 @@ func (h *HUOBI) GetTrades(symbol string) ([]Trade, error) {
}
var result response
url := fmt.Sprintf("%s/%s", h.APIUrl, huobiMarketTrade)
urlPath := fmt.Sprintf("%s/%s", h.APIUrl, huobiMarketTrade)
err := h.SendHTTPRequest(common.EncodeURLValues(url, vals), &result)
err := h.SendHTTPRequest(common.EncodeURLValues(urlPath, vals), &result)
if result.ErrorMessage != "" {
return nil, errors.New(result.ErrorMessage)
}
@@ -249,7 +249,7 @@ func (h *HUOBI) GetLatestSpotPrice(symbol string) (float64, error) {
return 0, err
}
if len(list) == 0 {
return 0, errors.New("The length of the list is 0")
return 0, errors.New("the length of the list is 0")
}
return list[0].Trades[0].Price, nil
@@ -270,9 +270,9 @@ func (h *HUOBI) GetTradeHistory(symbol, size string) ([]TradeHistory, error) {
}
var result response
url := fmt.Sprintf("%s/%s", h.APIUrl, huobiMarketTradeHistory)
urlPath := fmt.Sprintf("%s/%s", h.APIUrl, huobiMarketTradeHistory)
err := h.SendHTTPRequest(common.EncodeURLValues(url, vals), &result)
err := h.SendHTTPRequest(common.EncodeURLValues(urlPath, vals), &result)
if result.ErrorMessage != "" {
return nil, errors.New(result.ErrorMessage)
}
@@ -290,9 +290,9 @@ func (h *HUOBI) GetMarketDetail(symbol string) (Detail, error) {
}
var result response
url := fmt.Sprintf("%s/%s", h.APIUrl, huobiMarketDetail)
urlPath := fmt.Sprintf("%s/%s", h.APIUrl, huobiMarketDetail)
err := h.SendHTTPRequest(common.EncodeURLValues(url, vals), &result)
err := h.SendHTTPRequest(common.EncodeURLValues(urlPath, vals), &result)
if result.ErrorMessage != "" {
return result.Tick, errors.New(result.ErrorMessage)
}
@@ -307,9 +307,9 @@ func (h *HUOBI) GetSymbols() ([]Symbol, error) {
}
var result response
url := fmt.Sprintf("%s/v%s/%s", h.APIUrl, huobiAPIVersion, huobiSymbols)
urlPath := fmt.Sprintf("%s/v%s/%s", h.APIUrl, huobiAPIVersion, huobiSymbols)
err := h.SendHTTPRequest(url, &result)
err := h.SendHTTPRequest(urlPath, &result)
if result.ErrorMessage != "" {
return nil, errors.New(result.ErrorMessage)
}
@@ -324,9 +324,9 @@ func (h *HUOBI) GetCurrencies() ([]string, error) {
}
var result response
url := fmt.Sprintf("%s/v%s/%s", h.APIUrl, huobiAPIVersion, huobiCurrencies)
urlPath := fmt.Sprintf("%s/v%s/%s", h.APIUrl, huobiAPIVersion, huobiCurrencies)
err := h.SendHTTPRequest(url, &result)
err := h.SendHTTPRequest(urlPath, &result)
if result.ErrorMessage != "" {
return nil, errors.New(result.ErrorMessage)
}
@@ -341,9 +341,9 @@ func (h *HUOBI) GetTimestamp() (int64, error) {
}
var result response
url := fmt.Sprintf("%s/v%s/%s", h.APIUrl, huobiAPIVersion, huobiTimestamp)
urlPath := fmt.Sprintf("%s/v%s/%s", h.APIUrl, huobiAPIVersion, huobiTimestamp)
err := h.SendHTTPRequest(url, &result)
err := h.SendHTTPRequest(urlPath, &result)
if result.ErrorMessage != "" {
return 0, errors.New(result.ErrorMessage)
}
@@ -476,7 +476,7 @@ func (h *HUOBI) CancelOpenOrdersBatch(accountID, symbol string) (CancelOpenOrder
err := h.SendAuthenticatedHTTPRequest(http.MethodPost, huobiBatchCancelOpenOrders, url.Values{}, data, &result)
if result.Data.FailedCount > 0 {
return result, fmt.Errorf("There were %v failed order cancellations", result.Data.FailedCount)
return result, fmt.Errorf("there were %v failed order cancellations", result.Data.FailedCount)
}
return result, err
@@ -835,7 +835,7 @@ func (h *HUOBI) SendHTTPRequest(path string, result interface{}) error {
}
// SendAuthenticatedHTTPRequest sends authenticated requests to the HUOBI API
func (h *HUOBI) SendAuthenticatedHTTPRequest(method, endpoint string, values url.Values, data interface{}, result interface{}) error {
func (h *HUOBI) SendAuthenticatedHTTPRequest(method, endpoint string, values url.Values, data, result interface{}) error {
if !h.AuthenticatedAPISupport {
return fmt.Errorf(exchange.WarningAuthenticatedRequestWithoutCredentialsSet, h.Name)
}
@@ -869,23 +869,23 @@ func (h *HUOBI) SendAuthenticatedHTTPRequest(method, endpoint string, values url
pemKey := strings.NewReader(h.APIAuthPEMKey)
pemBytes, err := ioutil.ReadAll(pemKey)
if err != nil {
return fmt.Errorf("Huobi unable to ioutil.ReadAll PEM key: %s", err)
return fmt.Errorf("%s unable to ioutil.ReadAll PEM key: %s", h.Name, err)
}
block, _ := pem.Decode(pemBytes)
if block == nil {
return fmt.Errorf("Huobi block is nil")
return fmt.Errorf("%s PEM block is nil", h.Name)
}
x509Encoded := block.Bytes
privKey, err := x509.ParseECPrivateKey(x509Encoded)
if err != nil {
return fmt.Errorf("Huobi unable to ParseECPrivKey: %s", err)
return fmt.Errorf("%s unable to ParseECPrivKey: %s", h.Name, err)
}
r, s, err := ecdsa.Sign(rand.Reader, privKey, common.GetSHA256([]byte(signature)))
if err != nil {
return fmt.Errorf("Huobi unable to sign: %s", err)
return fmt.Errorf("%s unable to sign: %s", h.Name, err)
}
privSig := r.Bytes()
@@ -893,28 +893,28 @@ func (h *HUOBI) SendAuthenticatedHTTPRequest(method, endpoint string, values url
values.Set("PrivateSignature", common.Base64Encode(privSig))
}
url := fmt.Sprintf("%s%s", h.APIUrl, endpoint)
url = common.EncodeURLValues(url, values)
urlPath := common.EncodeURLValues(
fmt.Sprintf("%s%s", h.APIUrl, endpoint), values,
)
var body []byte
if data != nil {
encoded, err := json.Marshal(data)
if err != nil {
return fmt.Errorf("Huobi unable to marshal data: %s", err)
return fmt.Errorf("%s unable to marshal data: %s", h.Name, err)
}
body = encoded
}
return h.SendPayload(method, url, headers, bytes.NewReader(body), result, true, h.Verbose)
return h.SendPayload(method, urlPath, headers, bytes.NewReader(body), result, true, h.Verbose)
}
// GetFee returns an estimate of fee based on type of transaction
func (h *HUOBI) GetFee(feeBuilder exchange.FeeBuilder) (float64, error) {
var fee float64
switch feeBuilder.FeeType {
case exchange.CryptocurrencyTradeFee:
if feeBuilder.FeeType == exchange.CryptocurrencyTradeFee {
fee = calculateTradingFee(feeBuilder.PurchasePrice, feeBuilder.Amount)
}
if fee < 0 {

View File

@@ -53,7 +53,7 @@ func (h *HUOBI) Run() {
exchCfg.BaseCurrencies = "USD"
h.BaseCurrencies = []string{"USD"}
errCNY = cfg.UpdateExchangeConfig(exchCfg)
errCNY = cfg.UpdateExchangeConfig(&exchCfg)
if errCNY != nil {
log.Errorf("%s failed to update config. %s\n", h.Name, errCNY)
return
@@ -165,7 +165,7 @@ func (h *HUOBI) GetAccountID() ([]Account, error) {
return acc, nil
}
//GetAccountInfo retrieves balances for all enabled currencies for the
// GetAccountInfo retrieves balances for all enabled currencies for the
// HUOBI exchange - to-do
func (h *HUOBI) GetAccountInfo() (exchange.AccountInfo, error) {
var info exchange.AccountInfo
@@ -261,24 +261,23 @@ func (h *HUOBI) SubmitOrder(p pair.CurrencyPair, side exchange.OrderSide, orderT
AccountID: int(accountID),
}
if side == exchange.BuyOrderSide && orderType == exchange.MarketOrderType {
switch {
case side == exchange.BuyOrderSide && orderType == exchange.MarketOrderType:
formattedType = SpotNewOrderRequestTypeBuyMarket
} else if side == exchange.SellOrderSide && orderType == exchange.MarketOrderType {
case side == exchange.SellOrderSide && orderType == exchange.MarketOrderType:
formattedType = SpotNewOrderRequestTypeSellMarket
} else if side == exchange.BuyOrderSide && orderType == exchange.LimitOrderType {
case side == exchange.BuyOrderSide && orderType == exchange.LimitOrderType:
formattedType = SpotNewOrderRequestTypeBuyLimit
params.Price = price
} else if side == exchange.SellOrderSide && orderType == exchange.LimitOrderType {
case side == exchange.SellOrderSide && orderType == exchange.LimitOrderType:
formattedType = SpotNewOrderRequestTypeSellLimit
params.Price = price
} else {
return submitOrderResponse, errors.New("Unsupported order type")
default:
return submitOrderResponse, errors.New("unsupported order type")
}
params.Type = formattedType
response, err := h.SpotNewOrder(params)
if response > 0 {
submitOrderResponse.OrderID = fmt.Sprintf("%v", response)
}
@@ -374,8 +373,8 @@ func (h *HUOBI) GetFeeByType(feeBuilder exchange.FeeBuilder) (float64, error) {
// GetActiveOrders retrieves any orders that are active/open
func (h *HUOBI) GetActiveOrders(getOrdersRequest exchange.GetOrdersRequest) ([]exchange.OrderDetail, error) {
if len(getOrdersRequest.Currencies) <= 0 {
return nil, errors.New("Currency must be supplied")
if len(getOrdersRequest.Currencies) == 0 {
return nil, errors.New("currency must be supplied")
}
side := ""
@@ -419,8 +418,8 @@ func (h *HUOBI) GetActiveOrders(getOrdersRequest exchange.GetOrdersRequest) ([]e
// GetOrderHistory retrieves account order information
// Can Limit response to specific order status
func (h *HUOBI) GetOrderHistory(getOrdersRequest exchange.GetOrdersRequest) ([]exchange.OrderDetail, error) {
if len(getOrdersRequest.Currencies) <= 0 {
return nil, errors.New("Currency must be supplied")
if len(getOrdersRequest.Currencies) == 0 {
return nil, errors.New("currency must be supplied")
}
states := "partial-canceled,filled,canceled"

View File

@@ -158,9 +158,9 @@ func (h *HUOBIHADAX) GetSpotKline(arg KlinesRequestParams) ([]KlineItem, error)
}
var result response
url := fmt.Sprintf("%s/%s", h.APIUrl, huobihadaxMarketHistoryKline)
urlPath := fmt.Sprintf("%s/%s", h.APIUrl, huobihadaxMarketHistoryKline)
err := h.SendHTTPRequest(common.EncodeURLValues(url, vals), &result)
err := h.SendHTTPRequest(common.EncodeURLValues(urlPath, vals), &result)
if result.ErrorMessage != "" {
return nil, errors.New(result.ErrorMessage)
}
@@ -178,9 +178,9 @@ func (h *HUOBIHADAX) GetMarketDetailMerged(symbol string) (DetailMerged, error)
}
var result response
url := fmt.Sprintf("%s/%s", h.APIUrl, huobihadaxMarketDetailMerged)
urlPath := fmt.Sprintf("%s/%s", h.APIUrl, huobihadaxMarketDetailMerged)
err := h.SendHTTPRequest(common.EncodeURLValues(url, vals), &result)
err := h.SendHTTPRequest(common.EncodeURLValues(urlPath, vals), &result)
if result.ErrorMessage != "" {
return result.Tick, errors.New(result.ErrorMessage)
}
@@ -202,9 +202,9 @@ func (h *HUOBIHADAX) GetDepth(symbol, depthType string) (Orderbook, error) {
}
var result response
url := fmt.Sprintf("%s/%s", h.APIUrl, huobihadaxMarketDepth)
urlPath := fmt.Sprintf("%s/%s", h.APIUrl, huobihadaxMarketDepth)
err := h.SendHTTPRequest(common.EncodeURLValues(url, vals), &result)
err := h.SendHTTPRequest(common.EncodeURLValues(urlPath, vals), &result)
if result.ErrorMessage != "" {
return result.Depth, errors.New(result.ErrorMessage)
}
@@ -224,9 +224,9 @@ func (h *HUOBIHADAX) GetTrades(symbol string) ([]Trade, error) {
}
var result response
url := fmt.Sprintf("%s/%s", h.APIUrl, huobihadaxMarketTrade)
urlPath := fmt.Sprintf("%s/%s", h.APIUrl, huobihadaxMarketTrade)
err := h.SendHTTPRequest(common.EncodeURLValues(url, vals), &result)
err := h.SendHTTPRequest(common.EncodeURLValues(urlPath, vals), &result)
if result.ErrorMessage != "" {
return nil, errors.New(result.ErrorMessage)
}
@@ -243,7 +243,7 @@ func (h *HUOBIHADAX) GetLatestSpotPrice(symbol string) (float64, error) {
return 0, err
}
if len(list) == 0 {
return 0, errors.New("The length of the list is 0")
return 0, errors.New("the length of the list is 0")
}
return list[0].Trades[0].Price, nil
@@ -264,9 +264,9 @@ func (h *HUOBIHADAX) GetTradeHistory(symbol, size string) ([]TradeHistory, error
}
var result response
url := fmt.Sprintf("%s/%s", h.APIUrl, huobihadaxMarketTradeHistory)
urlPath := fmt.Sprintf("%s/%s", h.APIUrl, huobihadaxMarketTradeHistory)
err := h.SendHTTPRequest(common.EncodeURLValues(url, vals), &result)
err := h.SendHTTPRequest(common.EncodeURLValues(urlPath, vals), &result)
if result.ErrorMessage != "" {
return nil, errors.New(result.ErrorMessage)
}
@@ -284,9 +284,9 @@ func (h *HUOBIHADAX) GetMarketDetail(symbol string) (Detail, error) {
}
var result response
url := fmt.Sprintf("%s/%s", h.APIUrl, huobihadaxMarketDetail)
urlPath := fmt.Sprintf("%s/%s", h.APIUrl, huobihadaxMarketDetail)
err := h.SendHTTPRequest(common.EncodeURLValues(url, vals), &result)
err := h.SendHTTPRequest(common.EncodeURLValues(urlPath, vals), &result)
if result.ErrorMessage != "" {
return result.Tick, errors.New(result.ErrorMessage)
}
@@ -301,9 +301,9 @@ func (h *HUOBIHADAX) GetSymbols() ([]Symbol, error) {
}
var result response
url := fmt.Sprintf("%s/v%s/%s/%s", h.APIUrl, huobihadaxAPIVersion, huobihadaxAPIName, huobihadaxSymbols)
urlPath := fmt.Sprintf("%s/v%s/%s/%s", h.APIUrl, huobihadaxAPIVersion, huobihadaxAPIName, huobihadaxSymbols)
err := h.SendHTTPRequest(url, &result)
err := h.SendHTTPRequest(urlPath, &result)
if result.ErrorMessage != "" {
return nil, errors.New(result.ErrorMessage)
}
@@ -318,9 +318,9 @@ func (h *HUOBIHADAX) GetCurrencies() ([]string, error) {
}
var result response
url := fmt.Sprintf("%s/v%s/%s/%s", h.APIUrl, huobihadaxAPIVersion, huobihadaxAPIName, huobihadaxCurrencies)
urlPath := fmt.Sprintf("%s/v%s/%s/%s", h.APIUrl, huobihadaxAPIVersion, huobihadaxAPIName, huobihadaxCurrencies)
err := h.SendHTTPRequest(url, &result)
err := h.SendHTTPRequest(urlPath, &result)
if result.ErrorMessage != "" {
return nil, errors.New(result.ErrorMessage)
}
@@ -335,9 +335,9 @@ func (h *HUOBIHADAX) GetTimestamp() (int64, error) {
}
var result response
url := fmt.Sprintf("%s/v%s/%s", h.APIUrl, huobihadaxAPIVersion, huobihadaxTimestamp)
urlPath := fmt.Sprintf("%s/v%s/%s", h.APIUrl, huobihadaxAPIVersion, huobihadaxTimestamp)
err := h.SendHTTPRequest(url, &result)
err := h.SendHTTPRequest(urlPath, &result)
if result.ErrorMessage != "" {
return 0, errors.New(result.ErrorMessage)
}
@@ -482,7 +482,7 @@ func (h *HUOBIHADAX) CancelOpenOrdersBatch(accountID, symbol string) (CancelOpen
err := h.SendAuthenticatedHTTPPostRequest(http.MethodPost, huobiHadaxBatchCancelOpenOrders, postBodyParams, &result)
if result.Data.FailedCount > 0 {
return result, fmt.Errorf("There were %v failed order cancellations", result.Data.FailedCount)
return result, fmt.Errorf("there were %v failed order cancellations", result.Data.FailedCount)
}
return result, err
@@ -851,11 +851,9 @@ func (h *HUOBIHADAX) SendAuthenticatedHTTPPostRequest(method, endpoint, postBody
hmac := common.GetHMAC(common.HashSHA256, []byte(payload), []byte(h.APISecret))
signatureParams.Set("Signature", common.Base64Encode(hmac))
url := fmt.Sprintf("%s%s", h.APIUrl, endpoint)
url = common.EncodeURLValues(url, signatureParams)
return h.SendPayload(method, url, headers, bytes.NewBufferString(postBodyValues), result, true, h.Verbose)
urlPath := common.EncodeURLValues(fmt.Sprintf("%s%s", h.APIUrl, endpoint),
signatureParams)
return h.SendPayload(method, urlPath, headers, bytes.NewBufferString(postBodyValues), result, true, h.Verbose)
}
// SendAuthenticatedHTTPRequest sends authenticated requests to the HUOBI API
@@ -879,17 +877,15 @@ func (h *HUOBIHADAX) SendAuthenticatedHTTPRequest(method, endpoint string, value
hmac := common.GetHMAC(common.HashSHA256, []byte(payload), []byte(h.APISecret))
values.Set("Signature", common.Base64Encode(hmac))
url := fmt.Sprintf("%s%s", h.APIUrl, endpoint)
url = common.EncodeURLValues(url, values)
return h.SendPayload(method, url, headers, bytes.NewBufferString(""), result, true, h.Verbose)
urlPath := common.EncodeURLValues(fmt.Sprintf("%s%s", h.APIUrl, endpoint),
values)
return h.SendPayload(method, urlPath, headers, bytes.NewBufferString(""), result, true, h.Verbose)
}
// GetFee returns an estimate of fee based on type of transaction
func (h *HUOBIHADAX) GetFee(feeBuilder exchange.FeeBuilder) (float64, error) {
var fee float64
switch feeBuilder.FeeType {
case exchange.CryptocurrencyTradeFee:
if feeBuilder.FeeType == exchange.CryptocurrencyTradeFee {
fee = calculateTradingFee(feeBuilder.PurchasePrice, feeBuilder.Amount)
}
if fee < 0 {
@@ -905,7 +901,7 @@ func calculateTradingFee(purchasePrice, amount float64) float64 {
}
// GetDepositWithdrawalHistory returns deposit or withdrawal data
func (h *HUOBIHADAX) GetDepositWithdrawalHistory(associatedID string, currency string, isDeposit bool, size int64) ([]History, error) {
func (h *HUOBIHADAX) GetDepositWithdrawalHistory(associatedID, currency string, isDeposit bool, size int64) ([]History, error) {
var resp = struct {
Response
Data []History `json:"data"`

View File

@@ -226,18 +226,19 @@ func (h *HUOBIHADAX) SubmitOrder(p pair.CurrencyPair, side exchange.OrderSide, o
AccountID: int(accountID),
}
if side == exchange.BuyOrderSide && orderType == exchange.MarketOrderType {
switch {
case side == exchange.BuyOrderSide && orderType == exchange.MarketOrderType:
formattedType = SpotNewOrderRequestTypeBuyMarket
} else if side == exchange.SellOrderSide && orderType == exchange.MarketOrderType {
case side == exchange.SellOrderSide && orderType == exchange.MarketOrderType:
formattedType = SpotNewOrderRequestTypeSellMarket
} else if side == exchange.BuyOrderSide && orderType == exchange.LimitOrderType {
case side == exchange.BuyOrderSide && orderType == exchange.LimitOrderType:
formattedType = SpotNewOrderRequestTypeBuyLimit
params.Price = price
} else if side == exchange.SellOrderSide && orderType == exchange.LimitOrderType {
case side == exchange.SellOrderSide && orderType == exchange.LimitOrderType:
formattedType = SpotNewOrderRequestTypeSellLimit
params.Price = price
} else {
return submitOrderResponse, errors.New("Unsupported order type")
default:
return submitOrderResponse, errors.New("unsupported order type")
}
params.Type = formattedType
@@ -339,8 +340,8 @@ func (h *HUOBIHADAX) GetFeeByType(feeBuilder exchange.FeeBuilder) (float64, erro
// GetActiveOrders retrieves any orders that are active/open
func (h *HUOBIHADAX) GetActiveOrders(getOrdersRequest exchange.GetOrdersRequest) ([]exchange.OrderDetail, error) {
if len(getOrdersRequest.Currencies) <= 0 {
return nil, errors.New("Currency must be supplied")
if len(getOrdersRequest.Currencies) == 0 {
return nil, errors.New("currency must be supplied")
}
side := ""
@@ -384,8 +385,8 @@ func (h *HUOBIHADAX) GetActiveOrders(getOrdersRequest exchange.GetOrdersRequest)
// GetOrderHistory retrieves account order information
// Can Limit response to specific order status
func (h *HUOBIHADAX) GetOrderHistory(getOrdersRequest exchange.GetOrdersRequest) ([]exchange.OrderDetail, error) {
if len(getOrdersRequest.Currencies) <= 0 {
return nil, errors.New("Currency must be supplied")
if len(getOrdersRequest.Currencies) == 0 {
return nil, errors.New("currency must be supplied")
}
states := "partial-canceled,filled,canceled"

View File

@@ -223,8 +223,8 @@ func (i *ItBit) GetOrders(walletID, symbol, status string, page, perPage int64)
// GetWalletTrades returns all trades for a specified wallet.
func (i *ItBit) GetWalletTrades(walletID string, params url.Values) (Records, error) {
resp := Records{}
url := fmt.Sprintf("/%s/%s/%s", itbitWallets, walletID, itbitTrades)
path := common.EncodeURLValues(url, params)
urlPath := fmt.Sprintf("/%s/%s/%s", itbitWallets, walletID, itbitTrades)
path := common.EncodeURLValues(urlPath, params)
err := i.SendAuthenticatedHTTPRequest(http.MethodGet, path, nil, &resp)
if err != nil {
@@ -239,8 +239,8 @@ func (i *ItBit) GetWalletTrades(walletID string, params url.Values) (Records, er
// GetFundingHistoryForWallet returns all funding history for a specified wallet.
func (i *ItBit) GetFundingHistoryForWallet(walletID string, params url.Values) (FundingRecords, error) {
resp := FundingRecords{}
url := fmt.Sprintf("/%s/%s/%s", itbitWallets, walletID, itbitFundingHistory)
path := common.EncodeURLValues(url, params)
urlPath := fmt.Sprintf("/%s/%s/%s", itbitWallets, walletID, itbitFundingHistory)
path := common.EncodeURLValues(urlPath, params)
err := i.SendAuthenticatedHTTPRequest(http.MethodGet, path, nil, &resp)
if err != nil {
@@ -282,8 +282,8 @@ func (i *ItBit) PlaceOrder(walletID, side, orderType, currency string, amount, p
// GetOrder returns an order by id.
func (i *ItBit) GetOrder(walletID string, params url.Values) (Order, error) {
resp := Order{}
url := fmt.Sprintf("/%s/%s/%s", itbitWallets, walletID, itbitOrders)
path := common.EncodeURLValues(url, params)
urlPath := fmt.Sprintf("/%s/%s/%s", itbitWallets, walletID, itbitOrders)
path := common.EncodeURLValues(urlPath, params)
err := i.SendAuthenticatedHTTPRequest(http.MethodGet, path, nil, &resp)
if err != nil {
@@ -347,7 +347,7 @@ func (i *ItBit) SendHTTPRequest(path string, result interface{}) error {
}
// SendAuthenticatedHTTPRequest sends an authenticated request to itBit
func (i *ItBit) SendAuthenticatedHTTPRequest(method string, path string, params map[string]interface{}, result interface{}) error {
func (i *ItBit) SendAuthenticatedHTTPRequest(method, path string, params map[string]interface{}, result interface{}) error {
if !i.AuthenticatedAPISupport {
return fmt.Errorf(exchange.WarningAuthenticatedRequestWithoutCredentialsSet, i.Name)
}
@@ -356,18 +356,18 @@ func (i *ItBit) SendAuthenticatedHTTPRequest(method string, path string, params
return errors.New("client ID not set")
}
request := make(map[string]interface{})
url := i.APIUrl + path
req := make(map[string]interface{})
urlPath := i.APIUrl + path
for key, value := range params {
request[key] = value
req[key] = value
}
PayloadJSON := []byte("")
var err error
if params != nil {
PayloadJSON, err = common.JSONEncode(request)
PayloadJSON, err = common.JSONEncode(req)
if err != nil {
return err
}
@@ -380,13 +380,13 @@ func (i *ItBit) SendAuthenticatedHTTPRequest(method string, path string, params
nonce := i.Nonce.GetValue(i.Name, false).String()
timestamp := strconv.FormatInt(time.Now().UnixNano()/1000000, 10)
message, err := common.JSONEncode([]string{method, url, string(PayloadJSON), nonce, timestamp})
message, err := common.JSONEncode([]string{method, urlPath, string(PayloadJSON), nonce, timestamp})
if err != nil {
return err
}
hash := common.GetSHA256([]byte(nonce + string(message)))
hmac := common.GetHMAC(common.HashSHA512, []byte(url+string(hash)), []byte(i.APISecret))
hmac := common.GetHMAC(common.HashSHA512, []byte(urlPath+string(hash)), []byte(i.APISecret))
signature := common.Base64Encode(hmac)
headers := make(map[string]string)
@@ -403,7 +403,7 @@ func (i *ItBit) SendAuthenticatedHTTPRequest(method string, path string, params
RequestID string `json:"requestId"`
}{}
err = i.SendPayload(method, url, headers, bytes.NewBuffer(PayloadJSON), &intermediary, true, i.Verbose)
err = i.SendPayload(method, urlPath, headers, bytes.NewBuffer(PayloadJSON), &intermediary, true, i.Verbose)
if err != nil {
return err
}

View File

@@ -189,7 +189,7 @@ func (i *ItBit) SubmitOrder(p pair.CurrencyPair, side exchange.OrderSide, orderT
}
if wallet == "" {
return submitOrderResponse, fmt.Errorf("No wallet found with currency: %s with amount >= %v", p.FirstCurrency.String(), amount)
return submitOrderResponse, fmt.Errorf("no wallet found with currency: %s with amount >= %v", p.FirstCurrency.String(), amount)
}
response, err := i.PlaceOrder(wallet, side.ToString(), orderType.ToString(), p.FirstCurrency.String(), amount, price, p.Pair().String(), "")

View File

@@ -175,7 +175,7 @@ func (k *Kraken) GetAssetPairs() (map[string]AssetPairs, error) {
// GetTicker returns ticker information from kraken
func (k *Kraken) GetTicker(symbol string) (Ticker, error) {
ticker := Ticker{}
tick := Ticker{}
values := url.Values{}
values.Set("pair", symbol)
@@ -189,25 +189,25 @@ func (k *Kraken) GetTicker(symbol string) (Ticker, error) {
err := k.SendHTTPRequest(path, &resp)
if err != nil {
return ticker, err
return tick, err
}
if len(resp.Error) > 0 {
return ticker, fmt.Errorf("Kraken error: %s", resp.Error)
return tick, fmt.Errorf("%s error: %s", k.Name, resp.Error)
}
for _, y := range resp.Data {
ticker.Ask, _ = strconv.ParseFloat(y.Ask[0], 64)
ticker.Bid, _ = strconv.ParseFloat(y.Bid[0], 64)
ticker.Last, _ = strconv.ParseFloat(y.Last[0], 64)
ticker.Volume, _ = strconv.ParseFloat(y.Volume[1], 64)
ticker.VWAP, _ = strconv.ParseFloat(y.VWAP[1], 64)
ticker.Trades = y.Trades[1]
ticker.Low, _ = strconv.ParseFloat(y.Low[1], 64)
ticker.High, _ = strconv.ParseFloat(y.High[1], 64)
ticker.Open, _ = strconv.ParseFloat(y.Open, 64)
tick.Ask, _ = strconv.ParseFloat(y.Ask[0], 64)
tick.Bid, _ = strconv.ParseFloat(y.Bid[0], 64)
tick.Last, _ = strconv.ParseFloat(y.Last[0], 64)
tick.Volume, _ = strconv.ParseFloat(y.Volume[1], 64)
tick.VWAP, _ = strconv.ParseFloat(y.VWAP[1], 64)
tick.Trades = y.Trades[1]
tick.Low, _ = strconv.ParseFloat(y.Low[1], 64)
tick.High, _ = strconv.ParseFloat(y.High[1], 64)
tick.Open, _ = strconv.ParseFloat(y.Open, 64)
}
return ticker, nil
return tick, nil
}
// GetTickers supports fetching multiple tickers from Kraken
@@ -231,23 +231,23 @@ func (k *Kraken) GetTickers(pairList string) (Tickers, error) {
}
if len(resp.Error) > 0 {
return nil, fmt.Errorf("Kraken error: %s", resp.Error)
return nil, fmt.Errorf("%s error: %s", k.Name, resp.Error)
}
tickers := make(Tickers)
for x, y := range resp.Data {
ticker := Ticker{}
ticker.Ask, _ = strconv.ParseFloat(y.Ask[0], 64)
ticker.Bid, _ = strconv.ParseFloat(y.Bid[0], 64)
ticker.Last, _ = strconv.ParseFloat(y.Last[0], 64)
ticker.Volume, _ = strconv.ParseFloat(y.Volume[1], 64)
ticker.VWAP, _ = strconv.ParseFloat(y.VWAP[1], 64)
ticker.Trades = y.Trades[1]
ticker.Low, _ = strconv.ParseFloat(y.Low[1], 64)
ticker.High, _ = strconv.ParseFloat(y.High[1], 64)
ticker.Open, _ = strconv.ParseFloat(y.Open, 64)
tickers[x] = ticker
tick := Ticker{}
tick.Ask, _ = strconv.ParseFloat(y.Ask[0], 64)
tick.Bid, _ = strconv.ParseFloat(y.Bid[0], 64)
tick.Last, _ = strconv.ParseFloat(y.Last[0], 64)
tick.Volume, _ = strconv.ParseFloat(y.Volume[1], 64)
tick.VWAP, _ = strconv.ParseFloat(y.VWAP[1], 64)
tick.Trades = y.Trades[1]
tick.Low, _ = strconv.ParseFloat(y.Low[1], 64)
tick.High, _ = strconv.ParseFloat(y.High[1], 64)
tick.Open, _ = strconv.ParseFloat(y.Open, 64)
tickers[x] = tick
}
return tickers, nil
}
@@ -273,7 +273,7 @@ func (k *Kraken) GetOHLC(symbol string) ([]OpenHighLowClose, error) {
}
if len(result.Error) != 0 {
return OHLC, fmt.Errorf("GetOHLC error: %s", result.Error)
return OHLC, fmt.Errorf("getOHLC error: %s", result.Error)
}
for _, y := range result.Data[symbol].([]interface{}) {
@@ -514,11 +514,11 @@ func (k *Kraken) GetTradeBalance(args ...TradeBalanceOptions) (TradeBalanceInfo,
params := url.Values{}
if args != nil {
if len(args[0].Aclass) != 0 {
if len(args[0].Aclass) > 0 {
params.Set("aclass", args[0].Aclass)
}
if len(args[0].Asset) != 0 {
if len(args[0].Asset) > 0 {
params.Set("asset", args[0].Asset)
}
@@ -572,19 +572,19 @@ func (k *Kraken) GetClosedOrders(args GetClosedOrdersOptions) (ClosedOrders, err
params.Set("userref", strconv.FormatInt(int64(args.UserRef), 10))
}
if len(args.Start) != 0 {
if len(args.Start) > 0 {
params.Set("start", args.Start)
}
if len(args.End) != 0 {
if len(args.End) > 0 {
params.Set("end", args.End)
}
if args.Ofs != 0 {
if args.Ofs > 0 {
params.Set("ofs", strconv.FormatInt(args.Ofs, 10))
}
if len(args.CloseTime) != 0 {
if len(args.CloseTime) > 0 {
params.Set("closetime", args.CloseTime)
}
@@ -635,7 +635,7 @@ func (k *Kraken) GetTradesHistory(args ...GetTradesHistoryOptions) (TradesHistor
params := url.Values{}
if args != nil {
if len(args[0].Type) != 0 {
if len(args[0].Type) > 0 {
params.Set("type", args[0].Type)
}
@@ -643,15 +643,15 @@ func (k *Kraken) GetTradesHistory(args ...GetTradesHistoryOptions) (TradesHistor
params.Set("trades", "true")
}
if len(args[0].Start) != 0 {
if len(args[0].Start) > 0 {
params.Set("start", args[0].Start)
}
if len(args[0].End) != 0 {
if len(args[0].End) > 0 {
params.Set("end", args[0].End)
}
if args[0].Ofs != 0 {
if args[0].Ofs > 0 {
params.Set("ofs", strconv.FormatInt(args[0].Ofs, 10))
}
}
@@ -723,23 +723,23 @@ func (k *Kraken) GetLedgers(args ...GetLedgersOptions) (Ledgers, error) {
params := url.Values{}
if args != nil {
if len(args[0].Aclass) != 0 {
if args[0].Aclass == "" {
params.Set("aclass", args[0].Aclass)
}
if len(args[0].Asset) != 0 {
if args[0].Asset == "" {
params.Set("asset", args[0].Asset)
}
if len(args[0].Type) != 0 {
if args[0].Type == "" {
params.Set("type", args[0].Type)
}
if len(args[0].Start) != 0 {
if args[0].Start == "" {
params.Set("start", args[0].Start)
}
if len(args[0].End) != 0 {
if args[0].End == "" {
params.Set("end", args[0].End)
}
@@ -827,19 +827,19 @@ func (k *Kraken) AddOrder(symbol, side, orderType string, volume, price, price2,
params.Set("leverage", strconv.FormatFloat(leverage, 'f', -1, 64))
}
if len(args.Oflags) != 0 {
if args.Oflags == "" {
params.Set("oflags", args.Oflags)
}
if len(args.StartTm) != 0 {
if args.StartTm == "" {
params.Set("starttm", args.StartTm)
}
if len(args.ExpireTm) != 0 {
if args.ExpireTm == "" {
params.Set("expiretm", args.ExpireTm)
}
if len(args.CloseOrderType) != 0 {
if args.CloseOrderType != "" {
params.Set("close[ordertype]", args.ExpireTm)
}
@@ -890,14 +890,14 @@ func (k *Kraken) CancelExistingOrder(txid string) (CancelOrderResponse, error) {
// error = array of error messages in the format of:
// <char-severity code><string-error category>:<string-error type>[:<string-extra info>]
// severity code can be E for error or W for warning
func GetError(errors []string) error {
for _, e := range errors {
func GetError(apiErrors []string) error {
const exchangeName = "Kraken"
for _, e := range apiErrors {
switch e[0] {
case 'W':
log.Warnf("Kraken API warning: %v\n", e[1:])
log.Warnf("%s API warning: %v\n", exchangeName, e[1:])
default:
return fmt.Errorf("Kraken API error: %v", e[1:])
return fmt.Errorf("%s API error: %v", exchangeName, e[1:])
}
}
@@ -969,8 +969,7 @@ func (k *Kraken) GetFee(feeBuilder exchange.FeeBuilder) (float64, error) {
}
for _, i := range depositMethods {
switch feeBuilder.BankTransactionType {
case exchange.WireTransfer:
if feeBuilder.BankTransactionType == exchange.WireTransfer {
if i.Method == "SynapsePay (US Wire)" {
fee = i.Fee
return fee, nil
@@ -1034,7 +1033,7 @@ func (k *Kraken) WithdrawStatus(currency, method string) ([]WithdrawStatusRespon
params := url.Values{}
params.Set("asset ", currency)
if len(method) != 0 {
if method != "" {
params.Set("method", method)
}

View File

@@ -563,13 +563,13 @@ func TestWithdrawStatus(t *testing.T) {
if areTestAPIKeysSet() {
_, err := k.WithdrawStatus(symbol.BTC, "")
if err == nil {
if err != nil {
t.Error("Test Failed - WithdrawStatus() error", err)
}
} else {
_, err := k.WithdrawStatus(symbol.BTC, "")
if err == nil {
t.Error("Test Failed - WithdrawStatus() error", err)
t.Error("Test Failed - GetDepositAddress() error can not be nil", err)
}
}
}

View File

@@ -87,17 +87,18 @@ func (k *Kraken) UpdateTicker(p pair.CurrencyPair, assetType string) (ticker.Pri
for _, x := range pairs {
for y, z := range tickers {
if common.StringContains(y, x.FirstCurrency.Upper().String()) && common.StringContains(y, x.SecondCurrency.Upper().String()) {
var tp ticker.Price
tp.Pair = x
tp.Last = z.Last
tp.Ask = z.Ask
tp.Bid = z.Bid
tp.High = z.High
tp.Low = z.Low
tp.Volume = z.Volume
ticker.ProcessTicker(k.GetName(), x, tp, assetType)
if !common.StringContains(y, x.FirstCurrency.Upper().String()) && !common.StringContains(y, x.SecondCurrency.Upper().String()) {
continue
}
var tp ticker.Price
tp.Pair = x
tp.Last = z.Last
tp.Ask = z.Ask
tp.Bid = z.Bid
tp.High = z.High
tp.Low = z.Low
tp.Volume = z.Volume
ticker.ProcessTicker(k.GetName(), x, tp, assetType)
}
}
return ticker.GetTicker(k.GetName(), p, assetType)
@@ -324,15 +325,15 @@ func (k *Kraken) GetActiveOrders(getOrdersRequest exchange.GetOrdersRequest) ([]
// GetOrderHistory retrieves account order information
// Can Limit response to specific order status
func (k *Kraken) GetOrderHistory(getOrdersRequest exchange.GetOrdersRequest) ([]exchange.OrderDetail, error) {
request := GetClosedOrdersOptions{}
req := GetClosedOrdersOptions{}
if getOrdersRequest.StartTicks.Unix() > 0 {
request.Start = fmt.Sprintf("%v", getOrdersRequest.StartTicks.Unix())
req.Start = fmt.Sprintf("%v", getOrdersRequest.StartTicks.Unix())
}
if getOrdersRequest.EndTicks.Unix() > 0 {
request.End = fmt.Sprintf("%v", getOrdersRequest.EndTicks.Unix())
req.End = fmt.Sprintf("%v", getOrdersRequest.EndTicks.Unix())
}
resp, err := k.GetClosedOrders(request)
resp, err := k.GetClosedOrders(req)
if err != nil {
return nil, err
}

View File

@@ -132,30 +132,28 @@ func (l *LakeBTC) GetTicker() (map[string]Ticker, error) {
result := make(map[string]Ticker)
var addresses []string
for k, v := range response {
var ticker Ticker
var tick Ticker
key := common.StringToUpper(k)
if v.Ask != nil {
ticker.Ask, _ = strconv.ParseFloat(v.Ask.(string), 64)
tick.Ask, _ = strconv.ParseFloat(v.Ask.(string), 64)
}
if v.Bid != nil {
ticker.Bid, _ = strconv.ParseFloat(v.Bid.(string), 64)
tick.Bid, _ = strconv.ParseFloat(v.Bid.(string), 64)
}
if v.High != nil {
ticker.High, _ = strconv.ParseFloat(v.High.(string), 64)
tick.High, _ = strconv.ParseFloat(v.High.(string), 64)
}
if v.Last != nil {
ticker.Last, _ = strconv.ParseFloat(v.Last.(string), 64)
tick.Last, _ = strconv.ParseFloat(v.Last.(string), 64)
}
if v.Low != nil {
ticker.Low, _ = strconv.ParseFloat(v.Low.(string), 64)
tick.Low, _ = strconv.ParseFloat(v.Low.(string), 64)
}
if v.Volume != nil {
ticker.Volume, _ = strconv.ParseFloat(v.Volume.(string), 64)
tick.Volume, _ = strconv.ParseFloat(v.Volume.(string), 64)
}
result[key] = ticker
addresses = append(addresses, key)
result[key] = tick
}
return result, nil
}
@@ -236,7 +234,7 @@ func (l *LakeBTC) Trade(isBuyOrder bool, amount, price float64, currency string)
}
if resp.Result != "order received" {
return resp, fmt.Errorf("Unexpected result: %s", resp.Result)
return resp, fmt.Errorf("unexpected result: %s", resp.Result)
}
return resp, nil

View File

@@ -117,13 +117,14 @@ func (l *LakeBTC) GetAccountInfo() (exchange.AccountInfo, error) {
var currencies []exchange.AccountCurrencyInfo
for x, y := range accountInfo.Balance {
for z, w := range accountInfo.Locked {
if z == x {
var exchangeCurrency exchange.AccountCurrencyInfo
exchangeCurrency.CurrencyName = common.StringToUpper(x)
exchangeCurrency.TotalValue, _ = strconv.ParseFloat(y, 64)
exchangeCurrency.Hold, _ = strconv.ParseFloat(w, 64)
currencies = append(currencies, exchangeCurrency)
if z != x {
continue
}
var exchangeCurrency exchange.AccountCurrencyInfo
exchangeCurrency.CurrencyName = common.StringToUpper(x)
exchangeCurrency.TotalValue, _ = strconv.ParseFloat(y, 64)
exchangeCurrency.Hold, _ = strconv.ParseFloat(w, 64)
currencies = append(currencies, exchangeCurrency)
}
}
@@ -227,7 +228,7 @@ func (l *LakeBTC) GetDepositAddress(cryptocurrency pair.CurrencyItem, _ string)
// submitted
func (l *LakeBTC) WithdrawCryptocurrencyFunds(withdrawRequest exchange.WithdrawRequest) (string, error) {
if withdrawRequest.Currency.String() != symbol.BTC {
return "", errors.New("Only BTC supported for withdrawals")
return "", errors.New("only BTC is supported for withdrawals")
}
resp, err := l.CreateWithdraw(withdrawRequest.Amount, withdrawRequest.Description)

View File

@@ -225,8 +225,6 @@ func (l *LocalBitcoins) EditAd(_ AdEdit, adID string) error {
}
resp := response{}
//request := make(map[string]interface{})
return l.SendAuthenticatedHTTPRequest(http.MethodPost, localbitcoinsAPIAdEdit+adID+"/", nil, &resp)
}

View File

@@ -207,7 +207,7 @@ func (l *LocalBitcoins) SubmitOrder(p pair.CurrencyPair, side exchange.OrderSide
if adID != "" {
submitOrderResponse.OrderID = adID
} else {
return submitOrderResponse, errors.New("Ad placed, but not found via API")
return submitOrderResponse, errors.New("ad placed, but not found via API")
}
return submitOrderResponse, err
@@ -254,8 +254,8 @@ func (l *LocalBitcoins) GetOrderInfo(orderID int64) (exchange.OrderDetail, error
// GetDepositAddress returns a deposit address for a specified currency
func (l *LocalBitcoins) GetDepositAddress(cryptocurrency pair.CurrencyItem, _ string) (string, error) {
if !strings.EqualFold(symbol.BTC, cryptocurrency.String()) {
return "", fmt.Errorf("Localbitcoins do not have support for currency %s just bitcoin",
cryptocurrency.String())
return "", fmt.Errorf("%s does not have support for currency %s, it only supports bitcoin",
l.Name, cryptocurrency.String())
}
return l.GetWalletAddress()
@@ -368,11 +368,13 @@ func (l *LocalBitcoins) GetOrderHistory(getOrdersRequest exchange.GetOrdersReque
}
status := ""
if trade.Data.ReleasedAt != "" && trade.Data.ReleasedAt != null {
switch {
case trade.Data.ReleasedAt != "" && trade.Data.ReleasedAt != null:
status = "Released"
} else if trade.Data.CanceledAt != "" && trade.Data.CanceledAt != null {
case trade.Data.CanceledAt != "" && trade.Data.CanceledAt != null:
status = "Cancelled"
} else if trade.Data.ClosedAt != "" && trade.Data.ClosedAt != null {
case trade.Data.ClosedAt != "" && trade.Data.ClosedAt != null:
status = "Closed"
}

View File

@@ -398,11 +398,11 @@ func (o *OKCoin) Trade(amount, price float64, symbol, orderType string) (int64,
}
// GetTradeHistory returns client trade history
func (o *OKCoin) GetTradeHistory(symbol string, TradeID int64) ([]Trades, error) {
func (o *OKCoin) GetTradeHistory(symbol string, tradeID int64) ([]Trades, error) {
result := []Trades{}
v := url.Values{}
v.Set("symbol", symbol)
v.Set("since", strconv.FormatInt(TradeID, 10))
v.Set("since", strconv.FormatInt(tradeID, 10))
err := o.SendAuthenticatedHTTPRequest(okcoinTradeHistory, v, &result)
@@ -414,7 +414,7 @@ func (o *OKCoin) GetTradeHistory(symbol string, TradeID int64) ([]Trades, error)
}
// BatchTrade initiates a trade by batch order
func (o *OKCoin) BatchTrade(orderData string, symbol, orderType string) (BatchTrade, error) {
func (o *OKCoin) BatchTrade(orderData, symbol, orderType string) (BatchTrade, error) {
v := url.Values{}
v.Set("orders_data", orderData)
v.Set("symbol", symbol)
@@ -811,7 +811,7 @@ func (o *OKCoin) FuturesTrade(amount, price float64, matchPrice, leverage int64,
// FuturesBatchTrade initiates a batch of futures contract trades
func (o *OKCoin) FuturesBatchTrade(orderData, symbol, contractType string, leverage int64, _ string) {
v := url.Values{} //to-do batch trade support for orders_data)
v := url.Values{} // to-do batch trade support for orders_data)
v.Set("symbol", symbol)
v.Set("contract_type", contractType)
v.Set("orders_data", orderData)

View File

@@ -34,12 +34,12 @@ func (o *OKCoin) PingHandler(_ string) error {
// AddChannel adds a new channel on the websocket client
func (o *OKCoin) AddChannel(channel string) error {
event := WebsocketEvent{"addChannel", channel}
json, err := common.JSONEncode(event)
data, err := common.JSONEncode(event)
if err != nil {
return err
}
return o.WebsocketConn.WriteMessage(websocket.TextMessage, json)
return o.WebsocketConn.WriteMessage(websocket.TextMessage, data)
}
// WsConnect initiates a websocket connection
@@ -144,8 +144,7 @@ func (o *OKCoin) WsHandleData() {
var currencyPairSlice []string
splitChar := common.SplitStrings(init[0].Channel, "_")
currencyPairSlice = append(currencyPairSlice,
common.StringToUpper(splitChar[3]))
currencyPairSlice = append(currencyPairSlice,
common.StringToUpper(splitChar[3]),
common.StringToUpper(splitChar[4]))
currencyPair := common.JoinStrings(currencyPairSlice, "-")
@@ -243,8 +242,8 @@ func (o *OKCoin) WsHandleData() {
newDeal.Amount, _ = strconv.ParseFloat(data[2].(string), 64)
newDeal.Timestamp, _ = data[3].(string)
newDeal.Type, _ = data[4].(string)
deals = append(deals, newDeal)
deals = append(deals, newDeal) // nolint: staticcheck
// TODO: will need to link this up
}
}
}

View File

@@ -153,32 +153,28 @@ func (o *OKCoin) GetAccountInfo() (exchange.AccountInfo, error) {
return response, err
}
var currencies []exchange.AccountCurrencyInfo
currencies = append(currencies, exchange.AccountCurrencyInfo{
CurrencyName: "BTC",
TotalValue: assets.Info.Funds.Free.BTC,
Hold: assets.Info.Funds.Freezed.BTC,
})
currencies = append(currencies, exchange.AccountCurrencyInfo{
CurrencyName: "LTC",
TotalValue: assets.Info.Funds.Free.LTC,
Hold: assets.Info.Funds.Freezed.LTC,
})
currencies = append(currencies, exchange.AccountCurrencyInfo{
CurrencyName: "USD",
TotalValue: assets.Info.Funds.Free.USD,
Hold: assets.Info.Funds.Freezed.USD,
})
currencies = append(currencies, exchange.AccountCurrencyInfo{
CurrencyName: "CNY",
TotalValue: assets.Info.Funds.Free.CNY,
Hold: assets.Info.Funds.Freezed.CNY,
})
var currencies = []exchange.AccountCurrencyInfo{
{
CurrencyName: "BTC",
TotalValue: assets.Info.Funds.Free.BTC,
Hold: assets.Info.Funds.Freezed.BTC,
},
{
CurrencyName: "LTC",
TotalValue: assets.Info.Funds.Free.LTC,
Hold: assets.Info.Funds.Freezed.LTC,
},
{
CurrencyName: "USD",
TotalValue: assets.Info.Funds.Free.USD,
Hold: assets.Info.Funds.Freezed.USD,
},
{
CurrencyName: "CNY",
TotalValue: assets.Info.Funds.Free.CNY,
Hold: assets.Info.Funds.Freezed.CNY,
},
}
response.Accounts = append(response.Accounts, exchange.Account{
Currencies: currencies,
})
@@ -204,20 +200,20 @@ func (o *OKCoin) GetExchangeHistory(p pair.CurrencyPair, assetType string) ([]ex
func (o *OKCoin) SubmitOrder(p pair.CurrencyPair, side exchange.OrderSide, orderType exchange.OrderType, amount, price float64, _ string) (exchange.SubmitOrderResponse, error) {
var submitOrderResponse exchange.SubmitOrderResponse
var oT string
if orderType == exchange.LimitOrderType {
switch orderType {
case exchange.LimitOrderType:
oT = "sell"
if side == exchange.BuyOrderSide {
oT = "buy"
} else {
oT = "sell"
}
} else if orderType == exchange.MarketOrderType {
case exchange.MarketOrderType:
oT = "sell_market"
if side == exchange.BuyOrderSide {
oT = "buy_market"
} else {
oT = "sell_market"
}
} else {
return submitOrderResponse, errors.New("Unsupported order type")
default:
return submitOrderResponse, errors.New("unsupported order type")
}
response, err := o.Trade(amount, price, p.Pair().String(), oT)

View File

@@ -481,10 +481,13 @@ func (o *OKEX) GetContractCandlestickData(symbol, typeInput, contractType string
// GetContractHoldingsNumber returns current number of holdings
func (o *OKEX) GetContractHoldingsNumber(symbol, contractType string) (number float64, contract string, err error) {
if err = o.CheckSymbol(symbol); err != nil {
err = o.CheckSymbol(symbol)
if err != nil {
return number, contract, err
}
if err = o.CheckContractType(contractType); err != nil {
err = o.CheckContractType(contractType)
if err != nil {
return number, contract, err
}
@@ -495,7 +498,8 @@ func (o *OKEX) GetContractHoldingsNumber(symbol, contractType string) (number fl
path := fmt.Sprintf("%s%s%s.do?%s", o.APIUrl, apiVersion, contractFutureHoldAmount, values.Encode())
var resp interface{}
if err = o.SendHTTPRequest(path, &resp); err != nil {
err = o.SendHTTPRequest(path, &resp)
if err != nil {
return number, contract, err
}
@@ -511,7 +515,7 @@ func (o *OKEX) GetContractHoldingsNumber(symbol, contractType string) (number fl
contract = holdingMap["contract_name"].(string)
}
}
return
return number, contract, err
}
// GetContractlimit returns upper and lower price limit
@@ -716,7 +720,10 @@ func (o *OKEX) SpotCancelOrder(symbol string, argOrderID int64) (int64, error) {
}
if res.ErrorCode != 0 {
return returnOrderID, fmt.Errorf("ErrCode:%d ErrMsg:%s", res.ErrorCode, o.ErrorCodes[strconv.Itoa(res.ErrorCode)])
return returnOrderID, fmt.Errorf("failed to cancel order. code: %d err: %s",
res.ErrorCode,
o.ErrorCodes[strconv.Itoa(res.ErrorCode)],
)
}
returnOrderID, _ = common.Int64FromString(res.OrderID)
@@ -755,7 +762,7 @@ func (o *OKEX) GetSpotTicker(symbol string) (SpotPrice, error) {
return resp, nil
}
//GetSpotMarketDepth returns Market Depth
// GetSpotMarketDepth returns Market Depth
func (o *OKEX) GetSpotMarketDepth(asd ActualSpotDepthRequestParams) (ActualSpotDepth, error) {
resp := SpotDepth{}
fullDepth := ActualSpotDepth{}
@@ -963,7 +970,7 @@ func (o *OKEX) SendAuthenticatedHTTPRequest(method string, values url.Values, re
err = common.JSONDecode(intermediary, &errCap)
if err == nil {
if !errCap.Result {
return fmt.Errorf("SendAuthenticatedHTTPRequest error - %s",
return fmt.Errorf("sendAuthenticatedHTTPRequest error - %s",
o.ErrorCodes[strconv.FormatInt(errCap.Error, 10)])
}
}
@@ -974,24 +981,24 @@ func (o *OKEX) SendAuthenticatedHTTPRequest(method string, values url.Values, re
// SetErrorDefaults sets the full error default list
func (o *OKEX) SetErrorDefaults() {
o.ErrorCodes = map[string]error{
//Spot Errors
"10000": errors.New("Required field, can not be null"),
"10001": errors.New("Request frequency too high to exceed the limit allowed"),
"10002": errors.New("System error"),
"10004": errors.New("Request failed - Your API key might need to be recreated"),
"10005": errors.New("'SecretKey' does not exist"),
"10006": errors.New("'Api_key' does not exist"),
"10007": errors.New("Signature does not match"),
"10008": errors.New("Illegal parameter"),
"10009": errors.New("Order does not exist"),
"10010": errors.New("Insufficient funds"),
"10011": errors.New("Amount too low"),
"10012": errors.New("Only btc_usd ltc_usd supported"),
"10013": errors.New("Only support https request"),
"10014": errors.New("Order price must be between 0 and 1,000,000"),
"10015": errors.New("Order price differs from current market price too much"),
"10016": errors.New("Insufficient coins balance"),
"10017": errors.New("API authorization error"),
// Spot Errors
"10000": errors.New("required field, can not be null"),
"10001": errors.New("request frequency too high to exceed the limit allowed"),
"10002": errors.New("system error"),
"10004": errors.New("request failed - Your API key might need to be recreated"),
"10005": errors.New("'secretKey' does not exist"),
"10006": errors.New("'api_key' does not exist"),
"10007": errors.New("signature does not match"),
"10008": errors.New("illegal parameter"),
"10009": errors.New("order does not exist"),
"10010": errors.New("insufficient funds"),
"10011": errors.New("amount too low"),
"10012": errors.New("only btc_usd ltc_usd supported"),
"10013": errors.New("only support https request"),
"10014": errors.New("order price must be between 0 and 1,000,000"),
"10015": errors.New("order price differs from current market price too much"),
"10016": errors.New("insufficient coins balance"),
"10017": errors.New("api authorization error"),
"10018": errors.New("borrow amount less than lower limit [usd:100,btc:0.1,ltc:1]"),
"10019": errors.New("loan agreement not checked"),
"10020": errors.New("rate cannot exceed 1%"),
@@ -999,119 +1006,119 @@ func (o *OKEX) SetErrorDefaults() {
"10023": errors.New("fail to get latest ticker"),
"10024": errors.New("balance not sufficient"),
"10025": errors.New("quota is full, cannot borrow temporarily"),
"10026": errors.New("Loan (including reserved loan) and margin cannot be withdrawn"),
"10027": errors.New("Cannot withdraw within 24 hrs of authentication information modification"),
"10028": errors.New("Withdrawal amount exceeds daily limit"),
"10029": errors.New("Account has unpaid loan, please cancel/pay off the loan before withdraw"),
"10031": errors.New("Deposits can only be withdrawn after 6 confirmations"),
"10032": errors.New("Please enabled phone/google authenticator"),
"10033": errors.New("Fee higher than maximum network transaction fee"),
"10034": errors.New("Fee lower than minimum network transaction fee"),
"10035": errors.New("Insufficient BTC/LTC"),
"10036": errors.New("Withdrawal amount too low"),
"10037": errors.New("Trade password not set"),
"10040": errors.New("Withdrawal cancellation fails"),
"10041": errors.New("Withdrawal address not exsit or approved"),
"10042": errors.New("Admin password error"),
"10043": errors.New("Account equity error, withdrawal failure"),
"10026": errors.New("loan (including reserved loan) and margin cannot be withdrawn"),
"10027": errors.New("cannot withdraw within 24 hrs of authentication information modification"),
"10028": errors.New("withdrawal amount exceeds daily limit"),
"10029": errors.New("account has unpaid loan, please cancel/pay off the loan before withdraw"),
"10031": errors.New("deposits can only be withdrawn after 6 confirmations"),
"10032": errors.New("please enabled phone/google authenticator"),
"10033": errors.New("fee higher than maximum network transaction fee"),
"10034": errors.New("fee lower than minimum network transaction fee"),
"10035": errors.New("insufficient BTC/LTC"),
"10036": errors.New("withdrawal amount too low"),
"10037": errors.New("trade password not set"),
"10040": errors.New("withdrawal cancellation fails"),
"10041": errors.New("withdrawal address not exsit or approved"),
"10042": errors.New("admin password error"),
"10043": errors.New("account equity error, withdrawal failure"),
"10044": errors.New("fail to cancel borrowing order"),
"10047": errors.New("this function is disabled for sub-account"),
"10048": errors.New("withdrawal information does not exist"),
"10049": errors.New("User can not have more than 50 unfilled small orders (amount<0.15BTC)"),
"10049": errors.New("user can not have more than 50 unfilled small orders (amount<0.15BTC)"),
"10050": errors.New("can't cancel more than once"),
"10051": errors.New("order completed transaction"),
"10052": errors.New("not allowed to withdraw"),
"10064": errors.New("after a USD deposit, that portion of assets will not be withdrawable for the next 48 hours"),
"10100": errors.New("User account frozen"),
"10100": errors.New("user account frozen"),
"10101": errors.New("order type is wrong"),
"10102": errors.New("incorrect ID"),
"10103": errors.New("the private otc order's key incorrect"),
"10216": errors.New("Non-available API"),
"1002": errors.New("The transaction amount exceed the balance"),
"1003": errors.New("The transaction amount is less than the minimum requirement"),
"1004": errors.New("The transaction amount is less than 0"),
"1007": errors.New("No trading market information"),
"1008": errors.New("No latest market information"),
"1009": errors.New("No order"),
"1010": errors.New("Different user of the cancelled order and the original order"),
"1011": errors.New("No documented user"),
"1013": errors.New("No order type"),
"1014": errors.New("No login"),
"1015": errors.New("No market depth information"),
"1017": errors.New("Date error"),
"1018": errors.New("Order failed"),
"1019": errors.New("Undo order failed"),
"1024": errors.New("Currency does not exist"),
"1025": errors.New("No chart type"),
"1026": errors.New("No base currency quantity"),
"1027": errors.New("Incorrect parameter may exceeded limits"),
"1028": errors.New("Reserved decimal failed"),
"1029": errors.New("Preparing"),
"1030": errors.New("Account has margin and futures, transactions can not be processed"),
"1031": errors.New("Insufficient Transferring Balance"),
"1032": errors.New("Transferring Not Allowed"),
"1035": errors.New("Password incorrect"),
"1036": errors.New("Google Verification code Invalid"),
"1037": errors.New("Google Verification code incorrect"),
"1038": errors.New("Google Verification replicated"),
"1039": errors.New("Message Verification Input exceed the limit"),
"1040": errors.New("Message Verification invalid"),
"1041": errors.New("Message Verification incorrect"),
"1042": errors.New("Wrong Google Verification Input exceed the limit"),
"1043": errors.New("Login password cannot be same as the trading password"),
"1044": errors.New("Old password incorrect"),
"10216": errors.New("non-available API"),
"1002": errors.New("the transaction amount exceed the balance"),
"1003": errors.New("the transaction amount is less than the minimum requirement"),
"1004": errors.New("the transaction amount is less than 0"),
"1007": errors.New("no trading market information"),
"1008": errors.New("no latest market information"),
"1009": errors.New("no order"),
"1010": errors.New("different user of the cancelled order and the original order"),
"1011": errors.New("no documented user"),
"1013": errors.New("no order type"),
"1014": errors.New("no login"),
"1015": errors.New("no market depth information"),
"1017": errors.New("date error"),
"1018": errors.New("order failed"),
"1019": errors.New("undo order failed"),
"1024": errors.New("currency does not exist"),
"1025": errors.New("no chart type"),
"1026": errors.New("no base currency quantity"),
"1027": errors.New("incorrect parameter may exceeded limits"),
"1028": errors.New("reserved decimal failed"),
"1029": errors.New("preparing"),
"1030": errors.New("account has margin and futures, transactions can not be processed"),
"1031": errors.New("insufficient Transferring Balance"),
"1032": errors.New("transferring Not Allowed"),
"1035": errors.New("password incorrect"),
"1036": errors.New("google Verification code Invalid"),
"1037": errors.New("google Verification code incorrect"),
"1038": errors.New("google Verification replicated"),
"1039": errors.New("message Verification Input exceed the limit"),
"1040": errors.New("message Verification invalid"),
"1041": errors.New("message Verification incorrect"),
"1042": errors.New("wrong Google Verification Input exceed the limit"),
"1043": errors.New("login password cannot be same as the trading password"),
"1044": errors.New("old password incorrect"),
"1045": errors.New("2nd Verification Needed"),
"1046": errors.New("Please input old password"),
"1048": errors.New("Account Blocked"),
"1201": errors.New("Account Deleted at 00: 00"),
"1202": errors.New("Account Not Exist"),
"1203": errors.New("Insufficient Balance"),
"1204": errors.New("Invalid currency"),
"1205": errors.New("Invalid Account"),
"1206": errors.New("Cash Withdrawal Blocked"),
"1207": errors.New("Transfer Not Support"),
"1208": errors.New("No designated account"),
"1209": errors.New("Invalid api"),
"1216": errors.New("Market order temporarily suspended. Please send limit order"),
"1217": errors.New("Order was sent at ±5% of the current market price. Please resend"),
"1218": errors.New("Place order failed. Please try again later"),
"1046": errors.New("please input old password"),
"1048": errors.New("account Blocked"),
"1201": errors.New("account Deleted at 00: 00"),
"1202": errors.New("account Not Exist"),
"1203": errors.New("insufficient Balance"),
"1204": errors.New("invalid currency"),
"1205": errors.New("invalid Account"),
"1206": errors.New("cash Withdrawal Blocked"),
"1207": errors.New("transfer Not Support"),
"1208": errors.New("no designated account"),
"1209": errors.New("invalid api"),
"1216": errors.New("market order temporarily suspended. Please send limit order"),
"1217": errors.New("order was sent at ±5% of the current market price. Please resend"),
"1218": errors.New("place order failed. Please try again later"),
// Errors for both
"HTTP ERROR CODE 403": errors.New("Too many requests, IP is shielded"),
"Request Timed Out": errors.New("Too many requests, IP is shielded"),
"HTTP ERROR CODE 403": errors.New("too many requests, IP is shielded"),
"Request Timed Out": errors.New("too many requests, IP is shielded"),
// contract errors
"405": errors.New("method not allowed"),
"20001": errors.New("User does not exist"),
"20002": errors.New("Account frozen"),
"20003": errors.New("Account frozen due to liquidation"),
"20004": errors.New("Contract account frozen"),
"20005": errors.New("User contract account does not exist"),
"20006": errors.New("Required field missing"),
"20007": errors.New("Illegal parameter"),
"20008": errors.New("Contract account balance is too low"),
"20009": errors.New("Contract status error"),
"20010": errors.New("Risk rate ratio does not exist"),
"20011": errors.New("Risk rate lower than 90%/80% before opening BTC position with 10x/20x leverage. or risk rate lower than 80%/60% before opening LTC position with 10x/20x leverage"),
"20012": errors.New("Risk rate lower than 90%/80% after opening BTC position with 10x/20x leverage. or risk rate lower than 80%/60% after opening LTC position with 10x/20x leverage"),
"20013": errors.New("Temporally no counter party price"),
"20014": errors.New("System error"),
"20015": errors.New("Order does not exist"),
"20016": errors.New("Close amount bigger than your open positions"),
"20017": errors.New("Not authorized/illegal operation"),
"20018": errors.New("Order price cannot be more than 103% or less than 97% of the previous minute price"),
"20019": errors.New("IP restricted from accessing the resource"),
"20001": errors.New("user does not exist"),
"20002": errors.New("account frozen"),
"20003": errors.New("account frozen due to liquidation"),
"20004": errors.New("contract account frozen"),
"20005": errors.New("user contract account does not exist"),
"20006": errors.New("required field missing"),
"20007": errors.New("illegal parameter"),
"20008": errors.New("contract account balance is too low"),
"20009": errors.New("contract status error"),
"20010": errors.New("risk rate ratio does not exist"),
"20011": errors.New("risk rate lower than 90%/80% before opening BTC position with 10x/20x leverage. or risk rate lower than 80%/60% before opening LTC position with 10x/20x leverage"),
"20012": errors.New("risk rate lower than 90%/80% after opening BTC position with 10x/20x leverage. or risk rate lower than 80%/60% after opening LTC position with 10x/20x leverage"),
"20013": errors.New("temporally no counter party price"),
"20014": errors.New("system error"),
"20015": errors.New("order does not exist"),
"20016": errors.New("close amount bigger than your open positions"),
"20017": errors.New("not authorized/illegal operation"),
"20018": errors.New("order price cannot be more than 103% or less than 97% of the previous minute price"),
"20019": errors.New("ip restricted from accessing the resource"),
"20020": errors.New("secretKey does not exist"),
"20021": errors.New("Index information does not exist"),
"20022": errors.New("Wrong API interface (Cross margin mode shall call cross margin API, fixed margin mode shall call fixed margin API)"),
"20023": errors.New("Account in fixed-margin mode"),
"20024": errors.New("Signature does not match"),
"20025": errors.New("Leverage rate error"),
"20026": errors.New("API Permission Error"),
"20021": errors.New("index information does not exist"),
"20022": errors.New("wrong API interface (Cross margin mode shall call cross margin API, fixed margin mode shall call fixed margin API)"),
"20023": errors.New("account in fixed-margin mode"),
"20024": errors.New("signature does not match"),
"20025": errors.New("leverage rate error"),
"20026": errors.New("api permission error"),
"20027": errors.New("no transaction record"),
"20028": errors.New("no such contract"),
"20029": errors.New("Amount is large than available funds"),
"20030": errors.New("Account still has debts"),
"20038": errors.New("Due to regulation, this function is not available in the country/region your currently reside in"),
"20049": errors.New("Request frequency too high"),
"20029": errors.New("amount is large than available funds"),
"20030": errors.New("account still has debts"),
"20038": errors.New("due to regulation, this function is not available in the country/region your currently reside in"),
"20049": errors.New("request frequency too high"),
}
}

View File

@@ -61,8 +61,8 @@ func (o *OKEX) WsConnect() error {
err = o.WsSubscribe()
if err != nil {
return fmt.Errorf("Error: Could not subscribe to the OKEX websocket %s",
err)
return fmt.Errorf("%s could not subscribe to websocket %s",
o.Name, err)
}
return nil
@@ -90,17 +90,11 @@ func (o *OKEX) WsSubscribe() error {
myEnabledSubscriptionChannels = append(myEnabledSubscriptionChannels,
fmt.Sprintf("{'event':'addChannel','channel':'ok_sub_spot_%s_ticker'}",
symbolRedone))
myEnabledSubscriptionChannels = append(myEnabledSubscriptionChannels,
symbolRedone),
fmt.Sprintf("{'event':'addChannel','channel':'ok_sub_spot_%s_depth'}",
symbolRedone))
myEnabledSubscriptionChannels = append(myEnabledSubscriptionChannels,
symbolRedone),
fmt.Sprintf("{'event':'addChannel','channel':'ok_sub_spot_%s_deals'}",
symbolRedone))
myEnabledSubscriptionChannels = append(myEnabledSubscriptionChannels,
symbolRedone),
fmt.Sprintf("{'event':'addChannel','channel':'ok_sub_spot_%s_kline_1min'}",
symbolRedone))
}
@@ -221,7 +215,8 @@ func (o *OKEX) WsHandleData() {
assetType = currencyPairSlice[2]
}
if strings.Contains(multiStreamData.Channel, "ticker") {
switch multiStreamData.Channel {
case "ticker":
var ticker TickerStreamData
err = common.JSONDecode(multiStreamData.Data, &ticker)
@@ -235,8 +230,7 @@ func (o *OKEX) WsHandleData() {
Exchange: o.GetName(),
AssetType: assetType,
}
} else if strings.Contains(multiStreamData.Channel, "deals") {
case "deals":
var deals DealsStreamData
err = common.JSONDecode(multiStreamData.Data, &deals)
@@ -248,10 +242,10 @@ func (o *OKEX) WsHandleData() {
for _, trade := range deals {
price, _ := strconv.ParseFloat(trade[1], 64)
amount, _ := strconv.ParseFloat(trade[2], 64)
time, _ := time.Parse(time.RFC3339, trade[3])
tradeTime, _ := time.Parse(time.RFC3339, trade[3])
o.Websocket.DataHandler <- exchange.TradeData{
Timestamp: time,
Timestamp: tradeTime,
Exchange: o.GetName(),
AssetType: assetType,
CurrencyPair: pair.NewCurrencyPairFromString(newPair),
@@ -260,8 +254,7 @@ func (o *OKEX) WsHandleData() {
EventType: trade[4],
}
}
} else if strings.Contains(multiStreamData.Channel, "kline") {
case "kline":
var klines KlineStreamData
err := common.JSONDecode(multiStreamData.Data, &klines)
@@ -275,7 +268,7 @@ func (o *OKEX) WsHandleData() {
open, _ := strconv.ParseFloat(kline[1], 64)
high, _ := strconv.ParseFloat(kline[2], 64)
low, _ := strconv.ParseFloat(kline[3], 64)
close, _ := strconv.ParseFloat(kline[4], 64)
klineClose, _ := strconv.ParseFloat(kline[4], 64)
volume, _ := strconv.ParseFloat(kline[5], 64)
o.Websocket.DataHandler <- exchange.KlineData{
@@ -286,12 +279,11 @@ func (o *OKEX) WsHandleData() {
OpenPrice: open,
HighPrice: high,
LowPrice: low,
ClosePrice: close,
ClosePrice: klineClose,
Volume: volume,
}
}
} else if strings.Contains(multiStreamData.Channel, "depth") {
case "depth":
var depth DepthStreamData
err := common.JSONDecode(multiStreamData.Data, &depth)

View File

@@ -196,20 +196,19 @@ func (o *OKEX) SubmitOrder(p pair.CurrencyPair, side exchange.OrderSide, orderTy
var submitOrderResponse exchange.SubmitOrderResponse
var oT SpotNewOrderRequestType
if orderType == exchange.LimitOrderType {
switch orderType {
case exchange.LimitOrderType:
oT = SpotNewOrderRequestTypeSell
if side == exchange.BuyOrderSide {
oT = SpotNewOrderRequestTypeBuy
} else {
oT = SpotNewOrderRequestTypeSell
}
} else if orderType == exchange.MarketOrderType {
case exchange.MarketOrderType:
oT = SpotNewOrderRequestTypeSellMarket
if side == exchange.BuyOrderSide {
oT = SpotNewOrderRequestTypeBuyMarket
} else {
oT = SpotNewOrderRequestTypeSellMarket
}
} else {
return submitOrderResponse, errors.New("Unsupported order type")
default:
return submitOrderResponse, errors.New("unsupported order type")
}
var params = SpotNewOrderRequestParams{
@@ -263,7 +262,7 @@ func (o *OKEX) CancelAllOrders(_ exchange.OrderCancellation) (exchange.CancelAll
}
if !openOrders.Result {
return cancelAllOrdersResponse, fmt.Errorf("Something went wrong for currency %s", formattedCurrency)
return cancelAllOrdersResponse, fmt.Errorf("something went wrong for currency %s", formattedCurrency)
}
allOpenOrders = append(allOpenOrders, openOrders.Orders...)

View File

@@ -10,9 +10,9 @@ import (
// Const values for orderbook package
const (
ErrOrderbookForExchangeNotFound = "Ticker for exchange does not exist."
ErrPrimaryCurrencyNotFound = "Error primary currency for orderbook not found."
ErrSecondaryCurrencyNotFound = "Error secondary currency for orderbook not found."
ErrOrderbookForExchangeNotFound = "ticker for exchange does not exist"
ErrPrimaryCurrencyNotFound = "primary currency for orderbook not found"
ErrSecondaryCurrencyNotFound = "secondary currency for orderbook not found"
Spot = "SPOT"
)
@@ -48,9 +48,7 @@ type Orderbook struct {
// CalculateTotalBids returns the total amount of bids and the total orderbook
// bids value
func (o *Base) CalculateTotalBids() (float64, float64) {
amountCollated := float64(0)
total := float64(0)
func (o *Base) CalculateTotalBids() (amountCollated, total float64) {
for _, x := range o.Bids {
amountCollated += x.Amount
total += x.Amount * x.Price
@@ -60,9 +58,7 @@ func (o *Base) CalculateTotalBids() (float64, float64) {
// CalculateTotalAsks returns the total amount of asks and the total orderbook
// asks value
func (o *Base) CalculateTotalAsks() (float64, float64) {
amountCollated := float64(0)
total := float64(0)
func (o *Base) CalculateTotalAsks() (amountCollated, total float64) {
for _, x := range o.Asks {
amountCollated += x.Amount
total += x.Amount * x.Price
@@ -71,9 +67,9 @@ func (o *Base) CalculateTotalAsks() (float64, float64) {
}
// Update updates the bids and asks
func (o *Base) Update(Bids, Asks []Item) {
o.Bids = Bids
o.Asks = Asks
func (o *Base) Update(bids, asks []Item) {
o.Bids = bids
o.Asks = asks
o.LastUpdated = time.Now()
}
@@ -100,9 +96,9 @@ func GetOrderbook(exchange string, p pair.CurrencyPair, orderbookType string) (B
func GetOrderbookByExchange(exchange string) (*Orderbook, error) {
m.Lock()
defer m.Unlock()
for _, y := range Orderbooks {
if y.ExchangeName == exchange {
return &y, nil
for x := range Orderbooks {
if Orderbooks[x].ExchangeName == exchange {
return &Orderbooks[x], nil
}
}
return nil, errors.New(ErrOrderbookForExchangeNotFound)

View File

@@ -308,10 +308,12 @@ func TestProcessOrderbook(t *testing.T) {
for _, test := range testArray {
wg.Add(1)
fatalErr := false
go func(test quick) {
result, err := GetOrderbook(test.Name, test.P, Spot)
if err != nil {
t.Fatal("Test failed. TestProcessOrderbook failed to retrieve new orderbook")
fatalErr = true
return
}
if result.Asks[0] != test.Asks[0] {
@@ -324,6 +326,10 @@ func TestProcessOrderbook(t *testing.T) {
wg.Done()
}(test)
if fatalErr {
t.Fatal("Test failed. TestProcessOrderbook failed to retrieve new orderbook")
}
}
wg.Wait()

View File

@@ -18,7 +18,7 @@ type Order struct {
}
// NewOrder creates a new order and returns a an orderID
func NewOrder(Exchange string, amount, price float64) int {
func NewOrder(exchangeName string, amount, price float64) int {
order := &Order{}
if len(Orders) == 0 {
order.OrderID = 0
@@ -26,7 +26,7 @@ func NewOrder(Exchange string, amount, price float64) int {
order.OrderID = len(Orders)
}
order.Exchange = Exchange
order.Exchange = exchangeName
order.Amount = amount
order.Price = price
Orders = append(Orders, order)

View File

@@ -172,8 +172,8 @@ func (p *Poloniex) GetOrderbook(currencyPair string, depth int) (OrderbookAll, e
if err != nil {
return oba, err
}
if len(resp.Error) != 0 {
return oba, fmt.Errorf("Poloniex GetOrderbook() error: %s", resp.Error)
if resp.Error != "" {
return oba, fmt.Errorf("%s GetOrderbook() error: %s", p.Name, resp.Error)
}
ob := Orderbook{}
for x := range resp.Asks {
@@ -544,11 +544,11 @@ func (p *Poloniex) MoveOrder(orderID int64, rate, amount float64, postOnly, imme
values := url.Values{}
if orderID == 0 {
return result, errors.New("OrderID cannot be zero")
return result, errors.New("orderID cannot be zero")
}
if rate == 0 {
return result, errors.New("Rate cannot be zero")
return result, errors.New("rate cannot be zero")
}
values.Set("orderNumber", strconv.FormatInt(orderID, 10))

View File

@@ -7,7 +7,7 @@ import (
"github.com/thrasher-/gocryptotrader/config"
"github.com/thrasher-/gocryptotrader/currency/pair"
"github.com/thrasher-/gocryptotrader/currency/symbol"
"github.com/thrasher-/gocryptotrader/exchanges"
exchange "github.com/thrasher-/gocryptotrader/exchanges"
)
var p Poloniex
@@ -242,12 +242,12 @@ func TestSubmitOrder(t *testing.T) {
t.Skip("API keys set, canManipulateRealOrders false, skipping test")
}
var pair = pair.CurrencyPair{
var currencyPair = pair.CurrencyPair{
Delimiter: "_",
FirstCurrency: symbol.BTC,
SecondCurrency: symbol.LTC,
}
response, err := p.SubmitOrder(pair, exchange.BuyOrderSide, exchange.MarketOrderType, 1, 10, "hi")
response, err := p.SubmitOrder(currencyPair, exchange.BuyOrderSide, exchange.MarketOrderType, 1, 10, "hi")
if areTestAPIKeysSet() && (err != nil || !response.IsOrderPlaced) {
t.Errorf("Order failed to be placed: %v", err)
} else if !areTestAPIKeysSet() && err == nil {

View File

@@ -251,7 +251,7 @@ func (p *Poloniex) GetDepositAddress(cryptocurrency pair.CurrencyItem, _ string)
address, ok := a.Addresses[cryptocurrency.Upper().String()]
if !ok {
return "", fmt.Errorf("Cannot find deposit address for %s",
return "", fmt.Errorf("cannot find deposit address for %s",
cryptocurrency)
}

View File

@@ -368,20 +368,22 @@ func (r *Requester) worker() {
time.Sleep(diff)
for {
if !r.IsRateLimited(x.AuthRequest) {
r.IncrementRequests(x.AuthRequest)
if x.Verbose {
log.Debugf("%s request. No longer rate limited! Doing request", r.Name)
}
err := r.DoRequest(x.Request, x.Path, x.Body, x.Result, x.AuthRequest, x.Verbose)
x.JobResult <- &JobResult{
Error: err,
Result: x.Result,
}
break
if r.IsRateLimited(x.AuthRequest) {
time.Sleep(time.Millisecond)
continue
}
r.IncrementRequests(x.AuthRequest)
if x.Verbose {
log.Debugf("%s request. No longer rate limited! Doing request", r.Name)
}
err := r.DoRequest(x.Request, x.Path, x.Body, x.Result, x.AuthRequest, x.Verbose)
x.JobResult <- &JobResult{
Error: err,
Result: x.Result,
}
break
}
}
}
@@ -456,7 +458,7 @@ func (r *Requester) SendPayload(method, path string, headers map[string]string,
// SetProxy sets a proxy address to the client transport
func (r *Requester) SetProxy(p *url.URL) error {
if p.String() == "" {
return errors.New("No proxy URL supplied")
return errors.New("no proxy URL supplied")
}
r.HTTPClient.Transport = &http.Transport{

View File

@@ -8,15 +8,16 @@ import (
func TestLenByPrice(t *testing.T) {
p := pair.NewCurrencyPair("BTC", "USD")
i := Item{
Exchange: "ANX",
Pair: p,
AssetType: "SPOT",
Price: 1200,
Volume: 5,
Items = []Item{
{
Exchange: "ANX",
Pair: p,
AssetType: "SPOT",
Price: 1200,
Volume: 5,
},
}
Items = append(Items, i)
if ByPrice.Len(Items) < 1 {
t.Error("Test Failed - stats LenByPrice() length not correct.")
}
@@ -24,78 +25,77 @@ func TestLenByPrice(t *testing.T) {
func TestLessByPrice(t *testing.T) {
p := pair.NewCurrencyPair("BTC", "USD")
i := Item{
Exchange: "alphapoint",
Pair: p,
AssetType: "SPOT",
Price: 1200,
Volume: 5,
Items = []Item{
{
Exchange: "alphapoint",
Pair: p,
AssetType: "SPOT",
Price: 1200,
Volume: 5,
},
{
Exchange: "bitfinex",
Pair: p,
AssetType: "SPOT",
Price: 1198,
Volume: 20,
},
}
i2 := Item{
Exchange: "bitfinex",
Pair: p,
AssetType: "SPOT",
Price: 1198,
Volume: 20,
}
Items = append(Items, i)
Items = append(Items, i2)
if !ByPrice.Less(Items, 2, 1) {
if !ByPrice.Less(Items, 1, 0) {
t.Error("Test Failed - stats LessByPrice() incorrect return.")
}
if ByPrice.Less(Items, 1, 2) {
if ByPrice.Less(Items, 0, 1) {
t.Error("Test Failed - stats LessByPrice() incorrect return.")
}
}
func TestSwapByPrice(t *testing.T) {
p := pair.NewCurrencyPair("BTC", "USD")
i := Item{
Exchange: "bitstamp",
Pair: p,
AssetType: "SPOT",
Price: 1324,
Volume: 5,
Items = []Item{
{
Exchange: "bitstamp",
Pair: p,
AssetType: "SPOT",
Price: 1324,
Volume: 5,
},
{
Exchange: "btcc",
Pair: p,
AssetType: "SPOT",
Price: 7863,
Volume: 20,
},
}
i2 := Item{
Exchange: "btcc",
Pair: p,
AssetType: "SPOT",
Price: 7863,
Volume: 20,
}
Items = append(Items, i)
Items = append(Items, i2)
ByPrice.Swap(Items, 3, 4)
if Items[3].Exchange != "btcc" || Items[4].Exchange != "bitstamp" {
ByPrice.Swap(Items, 0, 1)
if Items[0].Exchange != "btcc" || Items[1].Exchange != "bitstamp" {
t.Error("Test Failed - stats SwapByPrice did not swap values.")
}
}
func TestLenByVolume(t *testing.T) {
if ByVolume.Len(Items) != 5 {
if ByVolume.Len(Items) != 2 {
t.Error("Test Failed - stats lenByVolume did not swap values.")
}
}
func TestLessByVolume(t *testing.T) {
if !ByVolume.Less(Items, 1, 2) {
if !ByVolume.Less(Items, 1, 0) {
t.Error("Test Failed - stats LessByVolume() incorrect return.")
}
if ByVolume.Less(Items, 2, 1) {
if ByVolume.Less(Items, 0, 1) {
t.Error("Test Failed - stats LessByVolume() incorrect return.")
}
}
func TestSwapByVolume(t *testing.T) {
ByPrice.Swap(Items, 3, 4)
ByPrice.Swap(Items, 0, 1)
if Items[4].Exchange != "btcc" || Items[3].Exchange != "bitstamp" {
if Items[1].Exchange != "btcc" || Items[0].Exchange != "bitstamp" {
t.Error("Test Failed - stats SwapByVolume did not swap values.")
}
}

View File

@@ -12,9 +12,9 @@ import (
// Const values for the ticker package
const (
ErrTickerForExchangeNotFound = "Ticker for exchange does not exist."
ErrPrimaryCurrencyNotFound = "Error primary currency for ticker not found."
ErrSecondaryCurrencyNotFound = "Error secondary currency for ticker not found."
ErrTickerForExchangeNotFound = "ticker for exchange does not exist"
ErrPrimaryCurrencyNotFound = "primary currency for ticker not found"
ErrSecondaryCurrencyNotFound = "secondary currency for ticker not found"
Spot = "SPOT"
)
@@ -91,9 +91,9 @@ func GetTicker(exchange string, p pair.CurrencyPair, tickerType string) (Price,
func GetTickerByExchange(exchange string) (*Ticker, error) {
m.Lock()
defer m.Unlock()
for _, y := range Tickers {
if y.ExchangeName == exchange {
return &y, nil
for x := range Tickers {
if Tickers[x].ExchangeName == exchange {
return &Tickers[x], nil
}
}
return nil, errors.New(ErrTickerForExchangeNotFound)

View File

@@ -200,6 +200,7 @@ func TestCreateNewTicker(t *testing.T) {
}
newTicker := CreateNewTicker("ANX", newPair, priceStruct, Spot)
const float64Type = "float64"
if reflect.ValueOf(newTicker).NumField() != 2 {
t.Error("Test Failed - ticker CreateNewTicker struct change/or updated")
@@ -214,33 +215,33 @@ func TestCreateNewTicker(t *testing.T) {
if newTicker.Price["BTC"]["USD"][Spot].Pair.Pair().String() != "BTCUSD" {
t.Error("Test Failed - ticker newTicker.Price[BTC][USD].Pair.Pair().String() value is not expected 'BTCUSD'")
}
if reflect.TypeOf(newTicker.Price["BTC"]["USD"][Spot].Ask).String() != "float64" {
if reflect.TypeOf(newTicker.Price["BTC"]["USD"][Spot].Ask).String() != float64Type {
t.Error("Test Failed - ticker newTicker.Price[BTC][USD].Ask value is not a float64")
}
if reflect.TypeOf(newTicker.Price["BTC"]["USD"][Spot].Bid).String() != "float64" {
if reflect.TypeOf(newTicker.Price["BTC"]["USD"][Spot].Bid).String() != float64Type {
t.Error("Test Failed - ticker newTicker.Price[BTC][USD].Bid value is not a float64")
}
if reflect.TypeOf(newTicker.Price["BTC"]["USD"][Spot].CurrencyPair).String() != "string" {
t.Error("Test Failed - ticker newTicker.Price[BTC][USD].CurrencyPair value is not a string")
}
if reflect.TypeOf(newTicker.Price["BTC"]["USD"][Spot].High).String() != "float64" {
if reflect.TypeOf(newTicker.Price["BTC"]["USD"][Spot].High).String() != float64Type {
t.Error("Test Failed - ticker newTicker.Price[BTC][USD].High value is not a float64")
}
if reflect.TypeOf(newTicker.Price["BTC"]["USD"][Spot].Last).String() != "float64" {
if reflect.TypeOf(newTicker.Price["BTC"]["USD"][Spot].Last).String() != float64Type {
t.Error("Test Failed - ticker newTicker.Price[BTC][USD].Last value is not a float64")
}
if reflect.TypeOf(newTicker.Price["BTC"]["USD"][Spot].Low).String() != "float64" {
if reflect.TypeOf(newTicker.Price["BTC"]["USD"][Spot].Low).String() != float64Type {
t.Error("Test Failed - ticker newTicker.Price[BTC][USD].Low value is not a float64")
}
if reflect.TypeOf(newTicker.Price["BTC"]["USD"][Spot].PriceATH).String() != "float64" {
if reflect.TypeOf(newTicker.Price["BTC"]["USD"][Spot].PriceATH).String() != float64Type {
t.Error("Test Failed - ticker newTicker.Price[BTC][USD].PriceATH value is not a float64")
}
if reflect.TypeOf(newTicker.Price["BTC"]["USD"][Spot].Volume).String() != "float64" {
if reflect.TypeOf(newTicker.Price["BTC"]["USD"][Spot].Volume).String() != float64Type {
t.Error("Test Failed - ticker newTicker.Price[BTC][USD].Volume value is not a float64")
}
}
func TestProcessTicker(t *testing.T) { //non-appending function to tickers
func TestProcessTicker(t *testing.T) { // non-appending function to tickers
Tickers = []Ticker{}
newPair := pair.NewCurrencyPair("BTC", "USD")
priceStruct := Price{
@@ -317,10 +318,12 @@ func TestProcessTicker(t *testing.T) { //non-appending function to tickers
for _, test := range testArray {
wg.Add(1)
fatalErr := false
go func(test quick) {
result, err := GetTicker(test.Name, test.P, Spot)
if err != nil {
t.Fatal("Test failed. TestProcessTicker failed to retrieve new ticker")
fatalErr = true
return
}
if result.Last != test.TP.Last {
@@ -329,6 +332,10 @@ func TestProcessTicker(t *testing.T) { //non-appending function to tickers
wg.Done()
}(test)
if fatalErr {
t.Fatal("Test failed. TestProcessTicker failed to retrieve new ticker")
}
}
wg.Wait()

View File

@@ -206,9 +206,9 @@ func (y *Yobit) GetOpenOrders(pair string) (map[string]ActiveOrders, error) {
}
// GetOrderInformation returns the order info for a specific order ID
func (y *Yobit) GetOrderInformation(OrderID int64) (map[string]OrderInfo, error) {
func (y *Yobit) GetOrderInformation(orderID int64) (map[string]OrderInfo, error) {
req := url.Values{}
req.Add("order_id", strconv.FormatInt(OrderID, 10))
req.Add("order_id", strconv.FormatInt(orderID, 10))
result := map[string]OrderInfo{}
@@ -216,9 +216,9 @@ func (y *Yobit) GetOrderInformation(OrderID int64) (map[string]OrderInfo, error)
}
// CancelExistingOrder cancels an order for a specific order ID
func (y *Yobit) CancelExistingOrder(OrderID int64) (bool, error) {
func (y *Yobit) CancelExistingOrder(orderID int64) (bool, error) {
req := url.Values{}
req.Add("order_id", strconv.FormatInt(OrderID, 10))
req.Add("order_id", strconv.FormatInt(orderID, 10))
result := CancelOrder{}
@@ -233,12 +233,12 @@ func (y *Yobit) CancelExistingOrder(OrderID int64) (bool, error) {
}
// GetTradeHistory returns the trade history
func (y *Yobit) GetTradeHistory(TIDFrom, Count, TIDEnd, since, end int64, order, pair string) (map[string]TradeHistory, error) {
func (y *Yobit) GetTradeHistory(tidFrom, count, tidEnd, since, end int64, order, pair string) (map[string]TradeHistory, error) {
req := url.Values{}
req.Add("from", strconv.FormatInt(TIDFrom, 10))
req.Add("count", strconv.FormatInt(Count, 10))
req.Add("from_id", strconv.FormatInt(TIDFrom, 10))
req.Add("end_id", strconv.FormatInt(TIDEnd, 10))
req.Add("from", strconv.FormatInt(tidFrom, 10))
req.Add("count", strconv.FormatInt(count, 10))
req.Add("from_id", strconv.FormatInt(tidFrom, 10))
req.Add("end_id", strconv.FormatInt(tidEnd, 10))
req.Add("order", order)
req.Add("since", strconv.FormatInt(since, 10))
req.Add("end", strconv.FormatInt(end, 10))
@@ -400,8 +400,7 @@ func getInternationalBankWithdrawalFee(currency string, amount float64, bankTran
switch bankTransactionType {
case exchange.PerfectMoney:
switch currency {
case symbol.USD:
if currency == symbol.USD {
fee = 0.02 * amount
}
case exchange.Payeer:
@@ -419,13 +418,11 @@ func getInternationalBankWithdrawalFee(currency string, amount float64, bankTran
fee = 0.03 * amount
}
case exchange.Qiwi:
switch currency {
case symbol.RUR:
if currency == symbol.RUR {
fee = 0.04 * amount
}
case exchange.Capitalist:
switch currency {
case symbol.USD:
if currency == symbol.USD {
fee = 0.06 * amount
}
}
@@ -438,8 +435,7 @@ func getInternationalBankDepositFee(currency string, bankTransactionType exchang
var fee float64
switch bankTransactionType {
case exchange.PerfectMoney:
switch currency {
case symbol.USD:
if currency == symbol.USD {
fee = 0
}
case exchange.Payeer:
@@ -457,8 +453,7 @@ func getInternationalBankDepositFee(currency string, bankTransactionType exchang
fee = 0
}
case exchange.Qiwi:
switch currency {
case symbol.RUR:
if currency == symbol.RUR {
fee = 0
}
case exchange.Capitalist:

View File

@@ -352,12 +352,12 @@ func TestSubmitOrder(t *testing.T) {
t.Skip("API keys set, canManipulateRealOrders false, skipping test")
}
var pair = pair.CurrencyPair{
var p = pair.CurrencyPair{
Delimiter: "_",
FirstCurrency: symbol.BTC,
SecondCurrency: symbol.USD,
}
response, err := y.SubmitOrder(pair, exchange.BuyOrderSide, exchange.MarketOrderType, 1, 10, "hi")
response, err := y.SubmitOrder(p, exchange.BuyOrderSide, exchange.MarketOrderType, 1, 10, "hi")
if areTestAPIKeysSet() && (err != nil || !response.IsOrderPlaced) {
t.Errorf("Order failed to be placed: %v", err)
} else if !areTestAPIKeysSet() && err == nil {

View File

@@ -105,7 +105,7 @@ type Trade struct {
Error string `json:"error"`
}
//TradeHistoryResponse returns all your trade history
// TradeHistoryResponse returns all your trade history
type TradeHistoryResponse struct {
Success int64 `json:"success"`
Data map[string]TradeHistory `json:"return,omitempty"`

View File

@@ -145,7 +145,7 @@ func (z *ZB) SpotNewOrder(arg SpotNewOrderRequestParams) (int64, error) {
return 0, err
}
if result.Code != 1000 {
return 0, fmt.Errorf("unsucessful new order, message: %s code: %d", result.Message, result.Code)
}
newOrderID, err := strconv.ParseInt(result.ID, 10, 64)
if err != nil {
@@ -220,10 +220,10 @@ func (z *ZB) GetOrders(currency string, pageindex, side int64) ([]Order, error)
// GetMarkets returns market information including pricing, symbols and
// each symbols decimal precision
func (z *ZB) GetMarkets() (map[string]MarketResponseItem, error) {
url := fmt.Sprintf("%s/%s/%s", z.APIUrl, zbAPIVersion, zbMarkets)
endpoint := fmt.Sprintf("%s/%s/%s", z.APIUrl, zbAPIVersion, zbMarkets)
var res interface{}
err := z.SendHTTPRequest(url, &res)
err := z.SendHTTPRequest(endpoint, &res)
if err != nil {
return nil, err
}
@@ -256,28 +256,28 @@ func (z *ZB) GetLatestSpotPrice(symbol string) (float64, error) {
// GetTicker returns a ticker for a given symbol
func (z *ZB) GetTicker(symbol string) (TickerResponse, error) {
url := fmt.Sprintf("%s/%s/%s?market=%s", z.APIUrl, zbAPIVersion, zbTicker, symbol)
urlPath := fmt.Sprintf("%s/%s/%s?market=%s", z.APIUrl, zbAPIVersion, zbTicker, symbol)
var res TickerResponse
err := z.SendHTTPRequest(url, &res)
err := z.SendHTTPRequest(urlPath, &res)
return res, err
}
// GetTickers returns ticker data for all supported symbols
func (z *ZB) GetTickers() (map[string]TickerChildResponse, error) {
url := fmt.Sprintf("%s/%s/%s", z.APIUrl, zbAPIVersion, zbTickers)
urlPath := fmt.Sprintf("%s/%s/%s", z.APIUrl, zbAPIVersion, zbTickers)
resp := make(map[string]TickerChildResponse)
err := z.SendHTTPRequest(url, &resp)
err := z.SendHTTPRequest(urlPath, &resp)
return resp, err
}
// GetOrderbook returns the orderbook for a given symbol
func (z *ZB) GetOrderbook(symbol string) (OrderbookResponse, error) {
url := fmt.Sprintf("%s/%s/%s?market=%s", z.APIUrl, zbAPIVersion, zbDepth, symbol)
urlPath := fmt.Sprintf("%s/%s/%s?market=%s", z.APIUrl, zbAPIVersion, zbDepth, symbol)
var res OrderbookResponse
err := z.SendHTTPRequest(url, &res)
err := z.SendHTTPRequest(urlPath, &res)
if err != nil {
return res, err
}
@@ -304,11 +304,11 @@ func (z *ZB) GetSpotKline(arg KlinesRequestParams) (KLineResponse, error) {
vals.Set("size", fmt.Sprintf("%d", arg.Size))
}
url := fmt.Sprintf("%s/%s/%s?%s", z.APIUrl, zbAPIVersion, zbKline, vals.Encode())
urlPath := fmt.Sprintf("%s/%s/%s?%s", z.APIUrl, zbAPIVersion, zbKline, vals.Encode())
var res KLineResponse
var rawKlines map[string]interface{}
err := z.SendHTTPRequest(url, &rawKlines)
err := z.SendHTTPRequest(urlPath, &rawKlines)
if err != nil {
return res, err
}
@@ -378,7 +378,7 @@ func (z *ZB) SendAuthenticatedHTTPRequest(httpMethod string, params url.Values,
params.Set("reqTime", fmt.Sprintf("%d", common.UnixMillis(time.Now())))
params.Set("sign", fmt.Sprintf("%x", hmac))
url := fmt.Sprintf("%s/%s?%s",
urlPath := fmt.Sprintf("%s/%s?%s",
z.APIUrlSecondary,
params.Get("method"),
params.Encode())
@@ -391,7 +391,7 @@ func (z *ZB) SendAuthenticatedHTTPRequest(httpMethod string, params url.Values,
}{}
err := z.SendPayload(httpMethod,
url,
urlPath,
nil,
strings.NewReader(""),
&intermediary,
@@ -404,7 +404,7 @@ func (z *ZB) SendAuthenticatedHTTPRequest(httpMethod string, params url.Values,
err = common.JSONDecode(intermediary, &errCap)
if err == nil {
if errCap.Code != 0 {
return fmt.Errorf("SendAuthenticatedHTTPRequest error code: %d message %s",
return fmt.Errorf("sendAuthenticatedHTTPRequest error code: %d message %s",
errCap.Code,
errorCode[errCap.Code])
}

View File

@@ -281,12 +281,13 @@ func TestSubmitOrder(t *testing.T) {
if areTestAPIKeysSet() && !canManipulateRealOrders {
t.Skip(fmt.Sprintf("ApiKey: %s. Can place orders: %v", z.APIKey, canManipulateRealOrders))
}
var pair = pair.CurrencyPair{
var currencyPair = pair.CurrencyPair{
Delimiter: "_",
FirstCurrency: symbol.QTUM,
SecondCurrency: symbol.USDT,
}
response, err := z.SubmitOrder(pair, exchange.BuyOrderSide, exchange.MarketOrderType, 1, 10, "hi")
response, err := z.SubmitOrder(currencyPair, exchange.BuyOrderSide, exchange.MarketOrderType, 1, 10, "hi")
if areTestAPIKeysSet() && (err != nil || !response.IsOrderPlaced) {
t.Errorf("Order failed to be placed: %v", err)
} else if !areTestAPIKeysSet() && err == nil {

View File

@@ -16,21 +16,21 @@ type OrderbookResponse struct {
// AccountsResponseCoin holds the accounts coin details
type AccountsResponseCoin struct {
Freez string `json:"freez"` //冻结资产
EnName string `json:"enName"` //币种英文名
UnitDecimal int `json:"unitDecimal"` //保留小数位
UnName string `json:"cnName"` //币种中文名
UnitTag string `json:"unitTag"` //币种符号
Available string `json:"available"` //可用资产
Key string `json:"key"` //币种
Freez string `json:"freez"` // 冻结资产
EnName string `json:"enName"` // 币种英文名
UnitDecimal int `json:"unitDecimal"` // 保留小数位
UnName string `json:"cnName"` // 币种中文名
UnitTag string `json:"unitTag"` // 币种符号
Available string `json:"available"` // 可用资产
Key string `json:"key"` // 币种
}
// AccountsBaseResponse holds basic account details
type AccountsBaseResponse struct {
UserName string `json:"username"` //用户名
TradePasswordEnabled bool `json:"trade_password_enabled"` //是否开通交易密码
AuthGoogleEnabled bool `json:"auth_google_enabled"` //是否开通谷歌验证
AuthMobileEnabled bool `json:"auth_mobile_enabled"` //是否开通手机验证
UserName string `json:"username"` // 用户名
TradePasswordEnabled bool `json:"trade_password_enabled"` // 是否开通交易密码
AuthGoogleEnabled bool `json:"auth_google_enabled"` // 是否开通谷歌验证
AuthMobileEnabled bool `json:"auth_mobile_enabled"` // 是否开通手机验证
}
// Order is the order details for retrieving all orders
@@ -51,10 +51,10 @@ type AccountsResponse struct {
Result struct {
Coins []AccountsResponseCoin `json:"coins"`
Base AccountsBaseResponse `json:"base"`
} `json:"result"` //用户名
AssetPerm bool `json:"assetPerm"` //是否开通交易密码
LeverPerm bool `json:"leverPerm"` //是否开通谷歌验证
EntrustPerm bool `json:"entrustPerm"` //是否开通手机验证
} `json:"result"` // 用户名
AssetPerm bool `json:"assetPerm"` // 是否开通交易密码
LeverPerm bool `json:"leverPerm"` // 是否开通谷歌验证
EntrustPerm bool `json:"entrustPerm"` // 是否开通手机验证
MoneyPerm bool `json:"moneyPerm"` // 资产列表
}
@@ -72,12 +72,12 @@ type TickerResponse struct {
// TickerChildResponse holds the ticker child response data
type TickerChildResponse struct {
Vol float64 `json:"vol,string"` //成交量(最近的24小时)
Last float64 `json:"last,string"` //最新成交价
Sell float64 `json:"sell,string"` //卖一价
Buy float64 `json:"buy,string"` //买一价
High float64 `json:"high,string"` //最高价
Low float64 `json:"low,string"` //最低价
Vol float64 `json:"vol,string"` // 成交量(最近的24小时)
Last float64 `json:"last,string"` // 最新成交价
Sell float64 `json:"sell,string"` // 卖一价
Buy float64 `json:"buy,string"` // 买一价
High float64 `json:"high,string"` // 最高价
Low float64 `json:"low,string"` // 最低价
}
// SpotNewOrderRequestParamsType ZB 交易类型
@@ -100,19 +100,19 @@ type SpotNewOrderRequestParams struct {
// SpotNewOrderResponse stores the new order response data
type SpotNewOrderResponse struct {
Code int `json:"code"` //返回代码
Message string `json:"message"` //提示信息
ID string `json:"id"` //委托挂单号
Code int `json:"code"` // 返回代码
Message string `json:"message"` // 提示信息
ID string `json:"id"` // 委托挂单号
}
// //-------------Kline
// KlinesRequestParams represents Klines request data.
type KlinesRequestParams struct {
Symbol string //交易对, zb_qc,zb_usdt,zb_btc...
Type TimeInterval //K线类型, 1min, 3min, 15min, 30min, 1hour......
Since string //从这个时间戳之后的
Size int //返回数据的条数限制(默认为1000如果返回数据多于1000条那么只返回1000条)
Symbol string // 交易对, zb_qc,zb_usdt,zb_btc...
Type TimeInterval // K线类型, 1min, 3min, 15min, 30min, 1hour......
Since string // 从这个时间戳之后的
Size int // 返回数据的条数限制(默认为1000如果返回数据多于1000条那么只返回1000条)
}
// KLineResponseData Kline Data

View File

@@ -10,7 +10,7 @@ import (
"github.com/gorilla/websocket"
"github.com/thrasher-/gocryptotrader/common"
"github.com/thrasher-/gocryptotrader/currency/pair"
"github.com/thrasher-/gocryptotrader/exchanges"
exchange "github.com/thrasher-/gocryptotrader/exchanges"
"github.com/thrasher-/gocryptotrader/exchanges/orderbook"
)

View File

@@ -340,7 +340,7 @@ func (z *ZB) GetActiveOrders(getOrdersRequest exchange.GetOrdersRequest) ([]exch
// This function is not concurrency safe due to orderSide/orderType maps
func (z *ZB) GetOrderHistory(getOrdersRequest exchange.GetOrdersRequest) ([]exchange.OrderDetail, error) {
if getOrdersRequest.OrderSide == exchange.AnyOrderSide || getOrdersRequest.OrderSide == "" {
return nil, errors.New("Specific order side is required")
return nil, errors.New("specific order side is required")
}
var allOrders []Order