Closed mark-antony1 closed 2 years ago
Did u guys solve this ? I got this error too.
Use the round function and round your quantity or price to the precision needed like:
quantity = float(round(quantity, precision))
best fix is quantity = float(round(quantity, 6))
decimal_count = 4
quantity = f"{float(value):.{decimal_count}f}"
All of this is not working for me
with quantity=round(self.quantity, self.precisions[self.coinName])
where, you guessed it, precisions is a dict of all needed precisions for each coin. This is still throwing an error.
I tried transforming it to string : same error. substracting random numbers from precision (1, 2, 3, ...) : same error. manually trying in a loop all possible precisions from 1 to 1000 : same error. Transforming it to DECIMAL : same error.
Help me please, I might cut my veins soon
@ArthurDetaille Try this:
_entryPrice = _entryPrice.rstrip("0").rstrip(".") if "." in _entryPrice else _entryPrice
decimal_count = len(str(_entryPrice).split(".")[1])
try:
self.order_limit(symbol, _amount, _side, _entryPrice, decimal_count)
except:
self.order_limit(symbol, _amount, _side, _entryPrice, decimal_count - 1) # here you are attempting with 1 lower decimal value
I'm afraid it's not working either :(
Allright, add me on discord 'Ærth uur#0767'
Maybe you could give you yours ? (thank again for your time)
I solve in this way: price = float(open_inf['entryPrice']) round_len = len(str(price).rsplit('.', 1)[-1]) (use round_len for your purposes, price - any that you get from binance)
tradingPairs = ['BTCUSDT','ETHUSDT','BNBUSDT']
#Loop though cryptos
for i in range(0,len(tradingPairs)):
info = client.futures_exchange_info()
if info['symbols'][0]['pair'] == tradingPairs[i]:
print("Price Pre ",info['symbols'][0]['pricePrecision'])
pricePrecision = info['symbols'][0]['pricePrecision']
quantityS = 5.2
quantityB = "{:0.0{}f}".format(quantityS, pricePrecision)
This is so frustrating I have been for a few days dealing with this, if not this error then other filter errors, isn't there any API to get to the closest feasible number that the exchange will accept?
And what about other exchanges? How do they manage this problem?
def normalize_number(self,my_float_number):
amount_int = int(float(my_float_number) / float(self.symbol.get_step_size()))
quote_step_size = float(self.symbol.get_step_size())
amount = 0
quote_asset_precision = self.symbol.get_base_asset_precision()
for i in range(0,amount_int):
amount = amount + quote_step_size
return "{:0.0{}f}".format(amount, quote_asset_precision)
def val(self):
min_qty_i_can_buy = self.symbol.min_quantity_i_can_buy()
max_qty_i_can_buy = self.symbol.max_quantity_i_can_buy()
if float(self.get_base_float()) <= max_qty_i_can_buy:
if float(self.get_base_float()) > min_qty_i_can_buy:
exchange_format_value = self.normalize_number(float(self.get_base_float()))
return float(exchange_format_value)
#return float(round(float(exchange_format_value),self.symbol.get_base_asset_precision()))
else:
exchange_format_value = self.normalize_number(float(self.symbol.min_quantity_i_can_buy()))
return exchange_format_value
And then I do:
float_amount = self.amount.val()
exchange.futures_create_order(symbol=symbol.uppercase_format(), side='BUY', type='MARKET', quantity=float_amount)
For Futures i used this and it worked very well
url = "https://api.binance.com/api/v3/exchangeInfo?symbol="+symbol info_data = requests.get(url).json() pricePrecision = info_data['symbols'][0]['baseAssetPrecision'] minQty = info_data['symbols'][0]['filters'][2]['minQty'] qtyTrueQ = info_data['symbols'][0]['filters'][1]['avgPriceMins'] quantityS = float(qtyTrueQ) quantityB = D.from_float(quantityS).quantize(D(str(pricePrecision)))
None of the answers you have given have helped me.
I have a variable with the available quantity on futures (av_quantity). And I want that when I create the order quantity = av_quantity and it gives me the "APIError (code = -1111): Precision is over the maximum defined for this asset".
Any suggestion?
def round_down( client, quantity, symbol):
info = client.get_symbol_info(symbol)
step_size = [float(_['stepSize']) for _ in info['filters'] if _['filterType'] == 'LOT_SIZE'][0]
step_size = '%.8f' % step_size
step_size = step_size.rstrip('0')
decimals = len(step_size.split('.')[1])
return math.floor(quantity * 10 ** decimals) / 10 ** decimals
hi .... I've seen that TP = float(round((tp) , 2)) only works with ethusdt .... how do I make it work for other pairs? how do I use the def described above? can make an example? thanks
Hey ! That. Is bit of a hassle but I found the way by using this on pyhon 3.9.5, THAT IS THE ONLY THING THAT WORKED FOR ME , I WASTED SO MUCH TIME ON THIS SH 1T
There is bina
from binance.helpers import round_step_size
def get_rounded_base_quantity(self):
return round_step_size((float(self.get_quote_value())/float(self.get_symbol().get_current_price())), float(self.get_symbol().get_step_size()))
On 2 Jan 2022, at 20:09, jsgaston @.***> wrote:
hi .... I've seen that TP = float(round((tp) , 2)) only works with ethusdt .... how do I make it work for other pairs? how do I use the def described above? can make an example? thanks
— Reply to this email directly, view it on GitHub https://github.com/sammchardy/python-binance/issues/296#issuecomment-1003768426, or unsubscribe https://github.com/notifications/unsubscribe-auth/ABDNE45YY44VIRDVDKO4M23UUCWGNANCNFSM4FFYSZCQ. Triage notifications on the go with GitHub Mobile for iOS https://apps.apple.com/app/apple-store/id1477376905?ct=notification-email&mt=8&pt=524675 or Android https://play.google.com/store/apps/details?id=com.github.android&referrer=utm_campaign%3Dnotification-email%26utm_medium%3Demail%26utm_source%3Dgithub. You are receiving this because you commented.
HI, can't make it work (just tried with bnbusdt) . I've imported the libreries. ... dont really know what to do to make it work... can u please tell me what I need to do to make it wokr?
If you
You can add me to telegram if you wish I am : @com_goldenthinker_trade_pablo
I noticed here that the trick with this is as follows, lets say you want to place an order to buy, ETHUSDT
You say to the exchange: create_market_buy_order worth for a quote amount of 20 USD
The exchange receives the order, but in between the exchange UPDATED THE PRICE, and the API only will accept EXACT numbers, and the quote amounts you pass have to be divisible per the new ETH quotation in USD.
The other solution is instead of passing the QUOTE value in USD, is to pass the BASE QUANTITY value you want to buy in ETH which is more exact and you do not depend on the timing and the exchange updating the price behind. BUT the amount that you pass have to be divisible per the STEP_SIZE of the base currency, that you can obtain from the EXCHANGE INFO API .
Is kind of a mess and the API should be able to accept and pass any number disregarding if it passes or does not pass the FILTERS. You should be able to pass ANY number, and the API should convert that number to the closest number that complies with the FILTERS. ]
Kind Regards
On 2 Jan 2022, at 20:44, jsgaston @.***> wrote:
HI, can't make it work (just tried with bnbusdt) . I've imported the libreries. ... dont really know what to do to make it work... can u tell me what I need to do to make it wokr?
— Reply to this email directly, view it on GitHub https://github.com/sammchardy/python-binance/issues/296#issuecomment-1003772386, or unsubscribe https://github.com/notifications/unsubscribe-auth/ABDNE4Y4TWOVBX7TPXNVRCDUUC2JHANCNFSM4FFYSZCQ. Triage notifications on the go with GitHub Mobile for iOS https://apps.apple.com/app/apple-store/id1477376905?ct=notification-email&mt=8&pt=524675 or Android https://play.google.com/store/apps/details?id=com.github.android&referrer=utm_campaign%3Dnotification-email%26utm_medium%3Demail%26utm_source%3Dgithub. You are receiving this because you commented.
I keep getting "APIEError(code=-1111): Precision is over the maximum defined for this asset" while I'm trying to execute a trade using a JSON payload that is sent from tradingview to my bot.
I have tried rounding the order amount before sending the request, this was successful in shortening the precision, but it resulted in the same error (resulted in a float being sent). I then tried using Decimal to shorten the precision, this was also successful in shortening the precision, but it resulted in the same error (decimal.Decimal was sent).
Here is my code:
Order Code:
def order(side, quantity, symbol, order_type=ORDER_TYPE_MARKET): try: print(f"sending order {order_type} - {side} {quantity} {symbol}") order = client.futures_create_order(symbol=symbol, side=side, type=order_type, quantity=quantity) except Exception as e: print("an exception occurred - {}".format(e)) return False
return order
Webapp code:
@app.route('/webhook3', methods=['POST'])
def webhook3():
print(request.data)
data = json.loads(request.data)
price = data["strategy"]["order_price"]
getcontext().prec = 6
urquantity = Decimal(str(lot3)) / Decimal(str(price))
if data["passphrase"] != config.WEBHOOK_PASSPHRASE:
return {
"code": "error",
"message": "Invalid Request"
}
side = data["strategy"]["order_action"].upper()
quantity = urquantity
symbol = data["ticker"]
order_response = order(side, quantity, symbol)
print(type(urquantity))
print(type(quantity))
I use insomnia to send the request to the locally hosted webapp and I get this result:
b'\n{\n "passphrase": "",\n "time": "2021-12-22T23:05:00Z",\n "exchange": "BINANCE",\n "ticker": "SUSHIUSDT",\n "bar": {\n "time": "2021-12-22T23:05:00Z",\n "open": 6.46,\n "high": 6.46,\n "low": 6.46,\n "close": 6.46,\n "volume": 5.1\n },\n "strategy": {\n "position_size": 100,\n "order_action" : "buy",\n "order_contracts": 10,\n "order_price": 6.46,\n "order_id": "long",\n "market_position": "long",\n "market_position_size": 10,\n "prev_marke t_position": "short",\n "prev_market_position_size": 0\n }\n}'
sending order MARKET - BUY 10.5139 SUSHIUSDT
an exception occurred - APIError(code=-1111): Precision is over the maximum defined for this asset.
<class 'decimal.Decimal'> <class 'decimal.Decimal'> order failed
I can only get orders to succeed if I send an int to Binance through the bot but even if the order is 10.5 it will still fail for the same error. Max precision is much higher than what I'm sending. If anyone has any suggestions or has a solution, your help would be greatly appreciated. I'm new to coding so my knowledge base is limited.
Thanks!
P.S. Pablo, you're a legend for trying to help so many people!
Has anyone a solution to create a order with decimals? I tried various ways for solving this problem, but didn't find one which is working. It also doesn't make sense to not accept floats which are formatted to the precision of the specific coin.
Has anyone found a solution? I am having the same issue
It's not exactly an easy answer (as far as I've been able to figure). First you need to get the quantity precision of the asset you want to trade. Lots of people mention step size and price precision, but if you have the same issues I did, it's actually quantityPrecision that's messing you up. If you're doing market orders, this is most likely your issue.
I wrote this to print out the quantity Precision for all of the symbols on Binance:
response_object = request.get("https://fapi.binance.com/fapi/v1/exchangeInfo")
for contract in response_object.json()['symbols']:
> print('QP_' + (contract['pair']) + ' = ' + str(contract['quantityPrecision']))
Then I added a truncate feature to my bot with this:
` import math
def truncate(number, decimals=0):
if not isinstance(decimals, int):
raise TypeError("decimal places must be an integer.") elif decimals < 0: raise ValueError("decimal places must be an integer.") elif decimals == 0: return math.trunc(number)
factor = 10.0 ** decimals return math.trunc(number + factor) / factor
`
THENNN, when I add quantity to my order I do it this way:
quantity = truncate(round((spend / price), quantityPrecision))
In the above, spend is just the amount I want to spend, price is the current price of the asset, and quantityPrecision is that precision I got from earlier. I round it because if you're truncating to 2 or 3 decimals places (2 or 3 precision), and your asset is worth $100, I feel like it's closer to what I want if I round it.
This is ugly, but it works. PS, I couldn't get the formatting to work well, but if you want more info on truncating just google it, that's where I got that block of code.
you can get these values from the exchange: GET /fapi/v1/exchangeInfo
Rounding to 1 decimal worked for me. I guess this comes from the new $0.1 tick size
API exchangeInfo https://api.binance.com/api/v3/exchangeInfo https://fapi.binance.com/fapi/v1/exchangeInfo
This is answer
API is still returning the wrong precision from endpoints. Any plans to solve this issue?
Yes, using quantityPrecision
solves my problem. This field comes from the interface:/exchangeInfo
eg:
var exchangeInfo = await getExchangeInfo();
exchangeInfo = JSON.parse(exchangeInfo);
var quantityPrecision = exchangeInfo.symbols.find(item => { return item.symbol === currency.symbol }).quantityPrecision
// 55 usdt
var quantity = new bigNumber(55).div(currency.price).toFixed(quantityPrecision);
await order({
symbol: currency.symbol,
side: 'BUY',
type: 'MARKET',
quantity,
positionSide: 'LONG', // BOTH 单一持仓操作 LONG 多头(双向持仓下)操作 SHORT 空头(双向持仓下)操作
timestamp: Date.now()
}).then(res => {
console.log(`success`, res);
}).catch(error => {
console.log(`line ${getCurrentLine()} error:`, error);
})
I had the same issue and solved it as following:
def getRoundCount(symbol):
exchance_info = binance_client.exchange_info()
symbols = exchance_info["symbols"]
for i in symbols:
if i["symbol"] == symbol:
filters = i["filters"]
df_filters = pd.DataFrame(filters)
df_filters.set_index("filterType", inplace=True)
lot_size_row = df_filters.loc["LOT_SIZE"]
minQty = lot_size_row["minQty"]
count_after_decimal = str(minQty)[::-1].find('.')
return count_after_decimal
Code might not be optimal since I am a beginner but it does the job.
There is an issue placing orders on binance for xmr/btc
The ticker information is as follows for the pair. {'symbol': 'XMRBTC', 'status': 'TRADING', 'baseAsset': 'XMR', 'baseAssetPrecision': 8, 'quoteAsset': 'BTC', 'quotePrecision': 8, 'orderTypes': ['LIMIT', 'LIMIT_MAKER', 'MARKET', 'STOP_LOSS_LIMIT', 'TAKE_PROFIT_LIMIT'], 'icebergAllowed': False, 'filters': [{'filterType': 'PRICE_FILTER', 'minPrice': '0.00000100', 'maxPrice': '100000.00000000', 'tickSize': '0.00000100'}, {'filterType': 'LOT_SIZE', 'minQty': '0.00100000', 'maxQty': '10000000.00000000', 'stepSize': '0.00100000'}, {'filterType': 'MIN_NOTIONAL', 'minNotional': '0.00100000'}]}
However, If i were to submit a buy where the quantity submitted is precise to 8 decimals, i.e. 0.44500000 It will return with the error binance.exceptions.BinanceAPIException: APIError(code=-1111): Precision is over the maximum defined for this asset.
What is the issue here?