def _query_margined_futures_balances( self, api_type: Literal['fapi', 'dapi'], balances: Dict, ) -> Dict: try: response = self.api_query_list(api_type, 'balance') except BinancePermissionError as e: log.warning( f'Insufficient permission to query {self.name} {api_type} balances.' f'Skipping query. Response details: {str(e)}', ) return balances try: for entry in response: amount = FVal(entry['balance']) if amount == ZERO: continue try: asset = asset_from_binance(entry['asset']) except UnsupportedAsset as e: self.msg_aggregator.add_warning( f'Found unsupported {self.name} asset {e.asset_name}. ' f'Ignoring its margined futures balance query.', ) continue except UnknownAsset as e: self.msg_aggregator.add_warning( f'Found unknown {self.name} asset {e.asset_name}. ' f'Ignoring its margined futures balance query.', ) continue except DeserializationError: self.msg_aggregator.add_error( f'Found {self.name} asset with non-string type ' f'{type(entry["asset"])}. Ignoring its margined futures balance query.', ) continue try: usd_price = Inquirer().find_usd_price(asset) except RemoteError as e: self.msg_aggregator.add_error( f'Error processing {self.name} balance entry due to inability to ' f'query USD price: {str(e)}. Skipping margined futures balance entry', ) continue balance = Balance(amount=amount, usd_value=amount * usd_price) if asset not in balances: balances[asset] = balance.to_dict() else: balances[asset]['amount'] += balance.amount balances[asset]['usd_value'] += balance.usd_value except KeyError as e: self.msg_aggregator.add_error( f'At {self.name} margined futures balance query did not find ' f'expected key {str(e)}. Skipping margined futures query...', ) return balances
def _query_lending_balances(self, balances: Dict) -> Dict: data = self.api_query_dict('sapi', 'lending/union/account') positions = data.get('positionAmountVos', None) if positions is None: raise RemoteError( f'Could not find key positionAmountVos in lending account data ' f'{data} returned by {self.name}.', ) for entry in positions: try: amount = FVal(entry['amount']) if amount == ZERO: continue asset = asset_from_binance(entry['asset']) except UnsupportedAsset as e: self.msg_aggregator.add_warning( f'Found unsupported {self.name} asset {e.asset_name}. ' f'Ignoring its lending balance query.', ) continue except UnknownAsset as e: self.msg_aggregator.add_warning( f'Found unknown {self.name} asset {e.asset_name}. ' f'Ignoring its lending balance query.', ) continue except (DeserializationError, KeyError) as e: msg = str(e) if isinstance(e, KeyError): msg = f'Missing key entry for {msg}.' self.msg_aggregator.add_error( f'Error at deserializing {self.name} asset. {msg}. ' f'Ignoring its lending balance query.', ) continue try: usd_price = Inquirer().find_usd_price(asset) except RemoteError as e: self.msg_aggregator.add_error( f'Error processing {self.name} balance entry due to inability to ' f'query USD price: {str(e)}. Skipping balance entry', ) continue balance = Balance(amount=amount, usd_value=amount * usd_price) if asset not in balances: balances[asset] = balance.to_dict() else: balances[asset]['amount'] += balance.amount balances[asset]['usd_value'] += balance.usd_value return balances
def _query_cross_collateral_futures_balances(self, balances: Dict) -> Dict: futures_response = self.api_query_dict('sapi', 'futures/loan/wallet') try: cross_collaterals = futures_response['crossCollaterals'] for entry in cross_collaterals: amount = FVal(entry['locked']) if amount == ZERO: continue try: asset = asset_from_binance(entry['collateralCoin']) except UnsupportedAsset as e: self.msg_aggregator.add_warning( f'Found unsupported {self.name} asset {e.asset_name}. ' f'Ignoring its futures balance query.', ) continue except UnknownAsset as e: self.msg_aggregator.add_warning( f'Found unknown {self.name} asset {e.asset_name}. ' f'Ignoring its futures balance query.', ) continue except DeserializationError: self.msg_aggregator.add_error( f'Found {self.name} asset with non-string type ' f'{type(entry["asset"])}. Ignoring its futures balance query.', ) continue try: usd_price = Inquirer().find_usd_price(asset) except RemoteError as e: self.msg_aggregator.add_error( f'Error processing {self.name} balance entry due to inability to ' f'query USD price: {str(e)}. Skipping balance entry', ) continue balance = Balance(amount=amount, usd_value=amount * usd_price) if asset not in balances: balances[asset] = balance.to_dict() else: balances[asset]['amount'] += balance.amount balances[asset]['usd_value'] += balance.usd_value except KeyError as e: self.msg_aggregator.add_error( f'At {self.name} futures balance query did not find expected key ' f'{str(e)}. Skipping futures query...', ) return balances