From f5f358e9d894bee593b5dab6879a03657b605f5c Mon Sep 17 00:00:00 2001 From: Michael Feng Date: Fri, 12 Jun 2026 06:58:33 -0700 Subject: [PATCH 1/4] feat: add default quote currencies for USDC/USD-quoted connectors Balance valuation falls back to fetching TOKEN- from the exchange when the rate oracle has no rate. The global default is USDT, which fails on exchanges that don't list USDT pairs, leaving tokens priced at 0 (e.g. BP on Backpack showed $0 and was hidden from portfolio views). Add entries for connectors whose markets quote in USDC (backpack, backpack_perpetual, cube, derive, derive_perpetual, dexalot, vertex, aevo_perpetual, pacifica_perpetual) and USD (dydx_v4_perpetual, decibel_perpetual, architect_perpetual), verified against each connector's pair construction in hummingbot. Co-Authored-By: Claude Fable 5 --- services/accounts_service.py | 12 ++++++++++++ 1 file changed, 12 insertions(+) diff --git a/services/accounts_service.py b/services/accounts_service.py index 9d48830e..5fe99105 100644 --- a/services/accounts_service.py +++ b/services/accounts_service.py @@ -442,6 +442,18 @@ class AccountsService: "hyperliquid_perpetual": "USD", "xrpl": "RLUSD", "kraken": "USD", + "backpack": "USDC", + "backpack_perpetual": "USDC", + "cube": "USDC", + "derive": "USDC", + "derive_perpetual": "USDC", + "dexalot": "USDC", + "vertex": "USDC", + "aevo_perpetual": "USDC", + "pacifica_perpetual": "USDC", + "dydx_v4_perpetual": "USD", + "decibel_perpetual": "USD", + "architect_perpetual": "USD", } potential_wrapped_tokens = ["ETH", "SOL", "BNB", "POL", "AVAX"] From 58786aef6d8c34f279f17277d8da711697b8adf1 Mon Sep 17 00:00:00 2001 From: Michael Feng Date: Fri, 12 Jun 2026 07:04:25 -0700 Subject: [PATCH 2/4] feat: default rate oracle source to gate_io instead of binance Binance's API returns HTTP 451 from geo-restricted locations, which silently breaks token valuation and anonymized-metrics volume conversion on fresh installs. Gate.io is accessible globally and lists the same USDT conversion pairs. Co-Authored-By: Claude Fable 5 --- main.py | 16 ++++++++++------ routers/rate_oracle.py | 4 ++-- 2 files changed, 12 insertions(+), 8 deletions(-) diff --git a/main.py b/main.py index 0f6e3d34..0a7e41cd 100644 --- a/main.py +++ b/main.py @@ -135,7 +135,7 @@ async def lifespan(app: FastAPI): # Get rate_oracle_source configuration rate_oracle_source_data = config_data.get("rate_oracle_source", {}) - source_name = rate_oracle_source_data.get("name", "binance") + source_name = rate_oracle_source_data.get("name", "gate_io") # Get global_token configuration global_token_data = config_data.get("global_token", {}) @@ -147,9 +147,9 @@ async def lifespan(app: FastAPI): rate_source = create_rate_source(source_name) logging.info(f"Configured RateOracle with source: {source_name}, quote_token: {quote_token}") else: - logging.warning(f"Unknown rate oracle source '{source_name}', defaulting to binance") - rate_source = create_rate_source("binance") - source_name = "binance" + logging.warning(f"Unknown rate oracle source '{source_name}', defaulting to gate_io") + rate_source = create_rate_source("gate_io") + source_name = "gate_io" # Initialize RateOracle with configured source and quote token rate_oracle = RateOracle.get_instance() @@ -157,11 +157,15 @@ async def lifespan(app: FastAPI): rate_oracle.quote_token = quote_token except FileNotFoundError: - logging.warning("conf_client.yml not found, using default RateOracle configuration (binance, USDT)") + logging.warning("conf_client.yml not found, using default RateOracle configuration (gate_io, USDT)") + from routers.rate_oracle import create_rate_source rate_oracle = RateOracle.get_instance() + rate_oracle.source = create_rate_source("gate_io") except Exception as e: - logging.warning(f"Error reading conf_client.yml: {e}, using default RateOracle configuration") + logging.warning(f"Error reading conf_client.yml: {e}, using default RateOracle configuration (gate_io)") + from routers.rate_oracle import create_rate_source rate_oracle = RateOracle.get_instance() + rate_oracle.source = create_rate_source("gate_io") # ========================================================================= # 2. UnifiedConnectorService - Single source of truth for all connectors diff --git a/routers/rate_oracle.py b/routers/rate_oracle.py index d4de548b..2aad210f 100644 --- a/routers/rate_oracle.py +++ b/routers/rate_oracle.py @@ -98,7 +98,7 @@ async def get_rate_oracle_config(request: Request): # Extract rate_oracle_source rate_oracle_source_data = config_data.get("rate_oracle_source", {}) - source_name = rate_oracle_source_data.get("name", "binance") + source_name = rate_oracle_source_data.get("name", "gate_io") # Extract global_token global_token_data = config_data.get("global_token", {}) @@ -196,7 +196,7 @@ async def update_rate_oracle_config( fs_util.dump_dict_to_yaml(CONF_CLIENT_PATH, config_data) # Build response - current_source = config_data.get("rate_oracle_source", {}).get("name", "binance") + current_source = config_data.get("rate_oracle_source", {}).get("name", "gate_io") current_global_token = config_data.get("global_token", {}) return RateOracleConfigUpdateResponse( From cf5006c842d371c1037e7f376b98c23549684fba Mon Sep 17 00:00:00 2001 From: Michael Feng Date: Fri, 12 Jun 2026 08:27:06 -0700 Subject: [PATCH 3/4] feat: default rate_oracle_source to gate_io in shipped conf_client.yml MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit The template always ships with an explicit rate_oracle_source, so the code-level defaults never apply on real installs — the shipped value must change too. Co-Authored-By: Claude Fable 5 --- bots/credentials/master_account/conf_client.yml | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/bots/credentials/master_account/conf_client.yml b/bots/credentials/master_account/conf_client.yml index cbba78d4..6fb8ba05 100644 --- a/bots/credentials/master_account/conf_client.yml +++ b/bots/credentials/master_account/conf_client.yml @@ -112,7 +112,7 @@ anonymized_metrics_mode: # A source for rate oracle, currently ascend_ex, binance, coin_gecko, coin_cap, kucoin, gate_io rate_oracle_source: - name: binance + name: gate_io # A universal token which to display tokens values in, e.g. USD,EUR,BTC global_token: From d8bbebf29302e44a11f73752448b4d741afaf0ed Mon Sep 17 00:00:00 2001 From: Michael Feng Date: Fri, 12 Jun 2026 08:33:06 -0700 Subject: [PATCH 4/4] feat: default rate oracle model to gate_io Aligns the API model default with the conf template and startup fallbacks. Co-Authored-By: Claude Fable 5 --- models/rate_oracle.py | 2 +- 1 file changed, 1 insertion(+), 1 deletion(-) diff --git a/models/rate_oracle.py b/models/rate_oracle.py index f0754f7b..35094fcf 100644 --- a/models/rate_oracle.py +++ b/models/rate_oracle.py @@ -24,7 +24,7 @@ class GlobalTokenConfig(BaseModel): class RateOracleSourceConfig(BaseModel): """Rate oracle source configuration.""" name: str = Field( - default="binance", + default="gate_io", description="The rate oracle source to use for price data" )