Hace algunos días leyendo por Internet vi como un amigo había hecho un BOT para Bittrex, aunque no usaba la API de Bittrex según leí por encima funcionaba bastante Bien, aunque note algunas inconsistencias de lógica, pero me sirvió para darme cuenta que no tenia que darme tantas vueltas con la idea y hacer primero un prototipo funcional y ya luego hacer un BOT mas especifico o como dicen por hay ir agregándole mas funcionalidad y robustez.
De aqui saque la estructura, mi colega @tstieff ojo no hice la estructura exactamente igual pero debería decirles algunas cosas que no deberían estar bien en el código anteriormente expuesto:
El código se conecta es a una serie de paginas con las claves, es como raspar la web o web scrapping, pero si tiene un poco de forma de API ya que los datos que devuelve son en un diccionario o JSON, lo que hice fue modificar el código y dejarlo casi funcional, mas adelante les digo por que casi.
Otra cosa importante para comprar y vender en Bittrex se necesita saber el mínimo que se puede comprar ademas del saldo o balance que se posea para comprar, si no tenemos saldo no podremos comprar nada y fallara, eso fue otra cosa rara que vi en el código ya veo por que el autor decia que el algoritmo era estupido , decía comprar o vender 5 siempre.
El código nuevo que mejore o hice quedo asi:
import time, requests, hashlib, hmac, urllib
BUY_ORDERBOOK = 'buy'
SELL_ORDERBOOK = 'sell'
BOTH_ORDERBOOK = 'both'
BASE_URL = 'https://bittrex.com/api/v1.1/%s/'
MARKET_SET = {'getopenorders', 'cancel', 'sellmarket', 'selllimit', 'buymarket', 'buylimit'}
ACCOUNT_SET = {'getbalances', 'getbalance', 'getdepositaddress', 'withdraw'}
class Bittrex(object):
def __init__(self, api_key, api_secret):
self.api_key = str(api_key) if api_key is not None else ''
self.api_secret = str(api_secret) if api_secret is not None else ''
def api_query(self, method, options={}):
nonce = str(int(time.time() * 1000))
method_set = 'public'
if method in MARKET_SET:
method_set = 'market'
elif method in ACCOUNT_SET:
method_set = 'account'
request_url = (BASE_URL % method_set) + method + '?'
if method_set != 'public':
request_url += 'apikey=' + self.api_key + "&nonce=" + nonce + '&'
request_url += urllib.urlencode(options)
return requests.get(
request_url,
headers={"apisign": hmac.new(self.api_secret.encode(), request_url.encode(), hashlib.sha512).hexdigest()}
).json()
def get_market_summaries(self):
return self.api_query('getmarketsummaries')
def buy_limit(self, market, quantity, rate):
return self.api_query('buylimit', {'market': market, 'quantity': quantity, 'rate': rate})
def sell_limit(self, market, quantity, rate):
return self.api_query('selllimit', {'market': market, 'quantity': quantity, 'rate': rate})
TICK_INTERVAL = 60 # seconds
API_KEY = 'MY TOKENs'
API_SECRET_KEY = 'MY TOKENs'
bittrex = Bittrex( API_KEY, API_SECRET_KEY )
def main():
print('START BOT...')
tick()
# Sleep the thread if needed
#if end - start < TICK_INTERVAL:
#time.sleep(TICK_INTERVAL - (end - start))
def tick():
print('RUNNING')
market_summaries = bittrex.get_market_summaries()
for summary in market_summaries['result']:
print summary
market = summary['MarketName']
day_close = summary['PrevDay']
last = summary['Last']
if day_close > 0:
percent_chg = ((last / day_close) - 1) * 100
else:
print ('day_close zero for ' + market)
print(market + ' changed ' + str(percent_chg))
print "Run other Crypto"
#if 40 < percent_chg < 60:
# Fomo strikes! Let's buy some
#print('Purchasing 5 units of ' + market + ' for ' + str(format_float(last)))
#res = buy_limit(market, 5, last)
#print(res)
#if percent_chg < -20:
# Ship is sinking, get out!
#print('Selling 5 units of ' + market + ' for ' + str(format_float(last)))
#res = sell_limit(market, 5, last)
#print(res)
def buy_limit(market, quantity, rate):
buy_limit = bittrex.buy_limit( market, quantity, rate)
return buy_limit
def sell_limit(market, quantity, rate):
sell_limit = bittrex.sell_limit( market, quantity, rate)
return sell_limit
def format_float(f):
return "%.8f" % f
if __name__ == "__main__":
main()
Agregue dentro del código la librería de Bittrex que vamos a usar, así que puedes copiar y pegar en un py y ya luego ejecutarlo y funcionara, solo asegurate de colocar tus Tokens de la API, de esta parte del codigo estoy hablando:
class Bittrex(object):
def __init__(self, api_key, api_secret):
self.api_key = str(api_key) if api_key is not None else ''
self.api_secret = str(api_secret) if api_secret is not None else ''
def api_query(self, method, options={}):
nonce = str(int(time.time() * 1000))
method_set = 'public'
if method in MARKET_SET:
method_set = 'market'
elif method in ACCOUNT_SET:
method_set = 'account'
request_url = (BASE_URL % method_set) + method + '?'
if method_set != 'public':
request_url += 'apikey=' + self.api_key + "&nonce=" + nonce + '&'
request_url += urllib.urlencode(options)
return requests.get(
request_url,
headers={"apisign": hmac.new(self.api_secret.encode(), request_url.encode(), hashlib.sha512).hexdigest()}
).json()
def get_market_summaries(self):
return self.api_query('getmarketsummaries')
def buy_limit(self, market, quantity, rate):
return self.api_query('buylimit', {'market': market, 'quantity': quantity, 'rate': rate})
def sell_limit(self, market, quantity, rate):
return self.api_query('selllimit', {'market': market, 'quantity': quantity, 'rate': rate})
Para Bittrex teníamos antes un Archivo ahora lo agregue a el mismo Archivo para solucionar problemas de compatibilidad o de ejecución.
En esa lista de funciones tenemos get_market_summaries, sell_limit, buy_limit con eso ahora mismo nos basta.
Luego cree la funcion main para correr el Script alli, luego la funcion tick() para ejecutar los tickets:
def tick():
print('RUNNING')
market_summaries = bittrex.get_market_summaries()
for summary in market_summaries['result']:
print summary
market = summary['MarketName']
day_close = summary['PrevDay']
last = summary['Last']
if day_close > 0:
percent_chg = ((last / day_close) - 1) * 100
else:
print ('day_close zero for ' + market)
print(market + ' changed ' + str(percent_chg))
print "Run other Crypto"
Es importante notar que esta funcion no compra ni vende nada debido a que aun nos hacen falta 2 cosas, la funcion para anular una compra o venta y la funcion para extraer el balance de lo que tenemos, como podemos vender algo que no tenemos???
La parte de comprar y vender segun haya cambiado el precio quedaria asi, ya en la otra entrada lo tendre esperemos:
#if 40 < percent_chg < 60:
# Fomo strikes! Let's buy some
#print('Purchasing 5 units of ' + market + ' for ' + str(format_float(last)))
#res = buy_limit(market, 5, last)
#print(res)
#if percent_chg < -20:
# Ship is sinking, get out!
#print('Selling 5 units of ' + market + ' for ' + str(format_float(last)))
#res = sell_limit(market, 5, last)
#print(res)
Luego tenemos estas 2 funciones que son muy importantes:
def buy_limit(market, quantity, rate):
buy_limit = bittrex.buy_limit( market, quantity, rate)
return buy_limit
def sell_limit(market, quantity, rate):
sell_limit = bittrex.sell_limit( market, quantity, rate)
return sell_limit
Son las Funciones que se conectan a la API y van a comprar y vender.
El Bot no lo hemos automatizado, debemos ejecutarlo manualmente podriamos crear un while y ejecutarlo infinitamente, pero ya solo nos queda agrear:
Ya estamos mas cerca y vamos con todo, les cuento que tengo otro proyecto paralaleo a Bittrex del que ya les hable y dio lugar a un gran proyecto de alarma comparador que voy a automatizar para la comunidad de Bittrex espero les guste.
Feliz Dia y Dios Bendiga a Venezuela