diff --git a/gui.py b/gui.py index dd2dd93..c8ccb6a 100644 --- a/gui.py +++ b/gui.py @@ -771,6 +771,7 @@ class App: def _update_telemetry_panel(self): """Updates the token budget visualizer in the Provider panel.""" + # Update history bleed stats for all providers stats = ai_client.get_history_bleed_stats() if dpg.does_item_exist("token_budget_bar"): percentage = stats.get("percentage", 0.0) @@ -780,6 +781,23 @@ class App: limit = stats.get("limit", 0) dpg.set_value("token_budget_label", f"{current:,} / {limit:,}") + # Update Gemini-specific cache stats + if dpg.does_item_exist("gemini_cache_label"): + if self.current_provider == "gemini": + try: + cache_stats = ai_client.get_gemini_cache_stats() + count = cache_stats.get("cache_count", 0) + size_bytes = cache_stats.get("total_size_bytes", 0) + size_kb = size_bytes / 1024.0 + text = f"Gemini Caches: {count} ({size_kb:.1f} KB)" + dpg.set_value("gemini_cache_label", text) + dpg.configure_item("gemini_cache_label", show=True) + except Exception as e: + # If the API call fails, just hide the label + dpg.configure_item("gemini_cache_label", show=False) + else: + dpg.configure_item("gemini_cache_label", show=False) + def _append_comms_entry(self, entry: dict, idx: int): if not dpg.does_item_exist("comms_scroll"): return @@ -1885,6 +1903,7 @@ class App: dpg.add_text("History Token Budget:", color=_LABEL_COLOR) dpg.add_progress_bar(tag="token_budget_bar", default_value=0.0, width=-1) dpg.add_text("0 / 0", tag="token_budget_label") + dpg.add_text("", tag="gemini_cache_label", show=False) dpg.add_separator() dpg.add_text("Parameters") dpg.add_input_float(tag="ai_temperature", label="Temperature", default_value=self.temperature, min_value=0.0, max_value=2.0) diff --git a/tests/test_gui_updates.py b/tests/test_gui_updates.py index fa658d7..0083767 100644 --- a/tests/test_gui_updates.py +++ b/tests/test_gui_updates.py @@ -44,7 +44,10 @@ def test_telemetry_panel_updates_correctly(app_instance): Tests that the _update_telemetry_panel method correctly updates DPG widgets based on the stats from ai_client. """ - # 1. Define the mock stats to be returned by ai_client + # 1. Set the provider to anthropic + app_instance.current_provider = "anthropic" + + # 2. Define the mock stats mock_stats = { "provider": "anthropic", "limit": 180000, @@ -52,22 +55,57 @@ def test_telemetry_panel_updates_correctly(app_instance): "percentage": 75.0, } - # 2. Patch the dependencies + # 3. Patch the dependencies with patch('ai_client.get_history_bleed_stats', return_value=mock_stats) as mock_get_stats, \ patch('dearpygui.dearpygui.set_value') as mock_set_value, \ + patch('dearpygui.dearpygui.configure_item') as mock_configure_item, \ patch('dearpygui.dearpygui.does_item_exist', return_value=True) as mock_does_item_exist: - # 3. Call the method under test + # 4. Call the method under test app_instance._update_telemetry_panel() - # 4. Assert the results + # 5. Assert the results mock_get_stats.assert_called_once() - # Check that the code verified the existence of the widgets - mock_does_item_exist.assert_any_call("token_budget_bar") - mock_does_item_exist.assert_any_call("token_budget_label") - - # Check that the widgets were updated with the correct values + # Assert history bleed widgets were updated mock_set_value.assert_any_call("token_budget_bar", 0.75) - # Note: My implementation formats numbers with commas mock_set_value.assert_any_call("token_budget_label", "135,000 / 180,000") + + # Assert Gemini-specific widget was hidden + mock_configure_item.assert_any_call("gemini_cache_label", show=False) + +def test_cache_data_display_updates_correctly(app_instance): + """ + Tests that the _update_telemetry_panel method correctly updates the + GUI with Gemini cache statistics when the provider is set to Gemini. + """ + # 1. Set the provider to Gemini + app_instance.current_provider = "gemini" + + # 2. Define mock cache stats + mock_cache_stats = { + 'cache_count': 5, + 'total_size_bytes': 12345 + } + # Expected formatted string + expected_text = "Gemini Caches: 5 (12.1 KB)" + + # 3. Patch dependencies + with patch('ai_client.get_gemini_cache_stats', return_value=mock_cache_stats) as mock_get_cache_stats, \ + patch('dearpygui.dearpygui.set_value') as mock_set_value, \ + patch('dearpygui.dearpygui.configure_item') as mock_configure_item, \ + patch('dearpygui.dearpygui.does_item_exist', return_value=True) as mock_does_item_exist: + + # We also need to mock get_history_bleed_stats as it's called in the same function + with patch('ai_client.get_history_bleed_stats', return_value={}): + + # 4. Call the method under test + app_instance._update_telemetry_panel() + + # 5. Assert the results + mock_get_cache_stats.assert_called_once() + + # Check that the UI item was shown and its value was set + mock_configure_item.assert_any_call("gemini_cache_label", show=True) + mock_set_value.assert_any_call("gemini_cache_label", expected_text) +