当我尝试使用“GET”方法从 Binance 获取历史蜡烛时,使用 Binance 的加密交易机器人,回调 > 绑定方法出错
Posted
技术标签:
【中文标题】当我尝试使用“GET”方法从 Binance 获取历史蜡烛时,使用 Binance 的加密交易机器人,回调 > 绑定方法出错【英文标题】:Crypto trading bot with Binance, Error from callback > bound method, when I am trying to get historical candles from Binance using the "GET" method 【发布时间】:2021-07-27 01:38:24 【问题描述】:机器人从 www.testnet.binancefuture.com 获取某些数据> 我得到的信息是买卖、历史蜡烛、合同、余额、下单、取消和订单状态。回调方法为 on_open、on_error、on_close 和 on_message + Channel 订阅。这是代码和错误
BinanceFuturesClient 类:
def __init__(self, public_key, secret_key, testnet):
if testnet:
self.base_url = "https://testnet.binancefuture.com"
self.wss_url = "wss://stream.binancefuture.com/ws"
else:
self.base_url = "https://fapi.binance.com"
self.wss_url = "wss://fstream.binance.com/ws"
self.public_key = public_key
self.secret_key = secret_key
self.headers = 'X-MBX-APIKEY': self.public_key
self.prices = dict()
self.id = 1
self.ws = None
t = threading.Thread(target=self.start_ws)
t.start()
logger.info("Binance Futures Client successfully initialized")
def generate_signature(self, data):
return hmac.new(self.secret_key.encode(), urlencode(data).encode(), hashlib.sha256).hexdigest()
def make_request(self, method, endpoint, data):
if method == "GET":
response = requests.get(self.base_url + endpoint, params=data, headers=self.headers)
elif method == 'POST':
response = requests.post(self.base_url + endpoint, params=data, headers=self.headers)
elif method == 'DELETE':
response = requests.delete(self.base_url + endpoint, params=data, headers=self.headers)
else:
raise ValueError()
if response.status_code == 200:
return response.json()
else:
logger.error('Error while making %s request to %s: %s(error code %s)',
method, endpoint, response.json(), response.status_code)
return None
def get_contracts(self):
exchange_info = self.make_request("GET", "/fapi/v1/exchangeInfo", None)
contracts = dict()
if exchange_info is not None:
for contract_data in exchange_info['symbols']:
contracts[contract_data['pair']] = contract_data
return contracts
def get_historical_candles(self, symbol, interval):
data = dict()
data['symbol'] = symbol
data['interval'] = interval
data['limit'] = 1000
raw_candles = self.make_request("GET", "/fapi/v1/klines", data)
candles = []
if raw_candles is not None:
for c in raw_candles:
candles.append([c[0], float(c[1]), float(c[2]), float(c[3]), float(c[4]), float(c[5])])
return candles
def get_bid_ask(self, symbol):
data = dict()
data['symbol'] = symbol
ob_data = self.make_request("GET", "/fapi/v1/ticker/bookTicker", data)
if ob_data is not None:
if symbol not in self.prices:
self.prices[symbol] = 'bid': float(ob_data['bidPrice']), 'ask': float(ob_data['askPrice'])
else:
self.prices[symbol]['bid'] = float(ob_data['bidPrice'])
self.prices[symbol]['ask'] = float(ob_data['askPrice'])
return self.prices[symbol]
def get_balances(self):
data = dict()
data['timestamp'] = int(time.time() * 1000)
data['signature'] = self.generate_signature(data)
balances = dict()
account_data = self.make_request("GET", "/fapi/v1/account", data)
if account_data is not None:
for a in account_data['assets']:
balances[a['asset']] = a
return balances
def place_order(self, symbol, side, quantity, order_type, price=None, tif=None):
data = dict()
data['symbol'] = symbol
data['side'] = side
data['quantity'] = quantity
data['type'] = order_type
if price is not None:
data['price'] = price
if tif is not None:
data['timeInForce'] = tif
data['timestamp'] = int(time.time() * 1000)
data['signature'] = self.generate_signature(data)
order_status = self.make_request("POST", "/fapi/v1/order", data)
return order_status
def cancel_order(self, symbol, order_id):
data = dict()
data['symbol'] = symbol
data['orderId'] = order_id
data['timestamp'] = int(time.time() * 1000)
data['signature'] = self.generate_signature(data)
order_status = self.make_request("DELETE", "/fapi/v1/order", data)
return order_status
def get_order_status(self, symbol, order_id):
data = dict()
data['timestamp'] = int(time.time() * 1000)
data['symbol'] = symbol
data['orderId'] = order_id
data['signature'] = self.generate_signature(data)
order_status = self.make_request("GET", "/fapi/v1/order", data)
return order_status
def start_ws(self):
ws = websocket.WebSocketApp(self.wss_url, on_open=self.on_open, on_close=self.on_close,
on_error=self.on_error, on_message=self.on_message)
ws.run_forever()
def on_close(self, ws):
logger.warning("Binance websocket connection closed")
def on_error(self, ws, msg):
logger.error("Binance connection error: %s", msg)
def on_open(self, ws):
logger.info("Binance connection opened")
self.subscribe_channel("BTCUSDT")
def on_message(self, ws, msg):
print(msg)
def subscribe_channel(self, symbol):
data = dict()
data['method'] = "SUBSCRIBE"
data['params'] = []
data['params'].append(symbol.lower() + "@bookTicker")
data['id'] = self.id
print(data, type(data))
print(json.dumps(data), type(json.dumps(data)))
self.ws.send(json.dumps(data))
self.id += 1
数据后的错误:
2021-05-04 16:51:55,683 INFO :: Binance Futures 客户端成功初始化
'method': 'SUBSCRIBE', 'params': ['btcusdt@bookTicker'], 'id': 1
【问题讨论】:
【参考方案1】:如下修改你的代码;
def start_ws(self):
self.ws = websocket.WebSocketApp(self.wss_url, on_open=self.on_open, on_close=self.on_close,
on_error=self.on_error, on_message=self.on_message)
self.ws.run_forever()
【讨论】:
以上是关于当我尝试使用“GET”方法从 Binance 获取历史蜡烛时,使用 Binance 的加密交易机器人,回调 > 绑定方法出错的主要内容,如果未能解决你的问题,请参考以下文章
如何使用 Binance API,通过股票代码简单 GET 价格
使用 Python(最好是请求)从 Binance API 获取烛台/Kline 数据以获取 JSON 数据
我正在尝试从 post 方法获取令牌,但我得到 json 响应 "Get/Method?Not Allowed" 我为此使用 POST 方法