File size: 6,234 Bytes
e324277
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
 
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
183
184
185
186
187
188
189
190
191
192
193
194
195
196
197
198
199
200
201
202
# P3 Bug: Progress Bar Positioning/Overlap in ChatInterface

**Severity**: P3 (Low - UX polish)
**Status**: Open
**Discovered**: 2025-12-01
**Reporter**: Internal QA

## Symptom

The `gr.Progress()` bar renders in a strange position when used inside `ChatInterface`:
- Progress bar appears to "float" in the middle of the chat output
- Text overlaps with progress bar elements
- Bar appears static/stuck at certain percentages
- Visual artifact: `Round 2/5 (~2m 15s remaining) - 48.0%` renders both above and inside bar

## Screenshot Evidence

Progress bar appears inline between chat messages rather than in a fixed position (top/bottom of component).

## Root Cause Analysis

### The Conflict

We're mixing **two different progress mechanisms**:

1. **`gr.Progress()`** - Gradio's general-purpose progress bar API
   - Designed for `gr.Interface` and `gr.Blocks` functions
   - Renders as an overlay on the output component

2. **`ChatInterface.show_progress`** - Built-in chat progress
   - Options: `"full"`, `"minimal"`, `"hidden"`
   - `"full"` = spinner + runtime display
   - `"minimal"` = runtime display only (default)

When both are used together in `ChatInterface`, the `gr.Progress()` bar fights for position with the chat's streaming output, causing visual glitches.

### Current Implementation (`src/app.py`)

```python
async def research_agent(
    message: str,
    history: list[dict[str, Any]],
    ...
    progress: gr.Progress = gr.Progress(),  # <- ISSUE: Manual progress bar
) -> AsyncGenerator[str, None]:
    ...
    if event.type == "started":
        progress(0, desc="Starting research...")  # <- Updates overlay
    elif event.type == "progress":
        progress(p, desc=event.message)  # <- Conflicts with chat streaming
```

### Gradio Documentation

From [Gradio ChatInterface Docs](https://www.gradio.app/docs/gradio/chatinterface):

> `show_progress`: how to show the progress animation while event is running: 'full' shows a spinner which covers the output component area as well as a runtime display in the upper right corner, 'minimal' only shows the runtime display, 'hidden' shows no progress animation at all

From [GitHub Issue #5967](https://github.com/gradio-app/gradio/issues/5967):

> `gr.Progress` is "not integrated with ChatInterface or Chatbots" - known limitation.

## Impact

| Aspect | Impact |
|--------|--------|
| Functionality | None - app works correctly |
| UX | Visual confusion, looks unprofessional |
| Accessibility | May cause screen reader confusion |

## Proposed Solutions

### Option 1: Remove `gr.Progress()` - Use Chat Text Only (RECOMMENDED)

Remove the `gr.Progress()` parameter entirely and rely on our existing emoji status messages:

```python
async def research_agent(
    message: str,
    history: list[dict[str, Any]],
    domain: str = "sexual_health",
    api_key: str = "",
    api_key_state: str = "",
    # REMOVED: progress: gr.Progress = gr.Progress(),
) -> AsyncGenerator[str, None]:
    ...
    # Keep emoji status updates in chat output
    # ⏱️ **PROGRESS**: Round 1/5 (~3m 0s remaining)
    # These are already being yielded to the chat
```

**Pros**:
- Simplest solution
- No CSS hacks
- Status is visible in chat history
- Works with ChatInterface's built-in progress

**Cons**:
- No visual progress bar (just text status)

### Option 2: Use `show_progress="full"` Parameter

Add explicit `show_progress` to ChatInterface and remove `gr.Progress()`:

```python
demo = gr.ChatInterface(
    fn=research_agent,
    title="🍆 DeepBoner",
    show_progress="full",  # Built-in spinner + runtime
    ...
)
```

**Pros**:
- Uses Gradio's intended mechanism
- Consistent with Gradio UX patterns

**Cons**:
- Less granular (no percentage, no custom desc)

### Option 3: Custom Progress Component with CSS (COMPLEX)

Wrap ChatInterface in `gr.Blocks` and add a separate `gr.HTML` progress bar outside the chat:

```python
with gr.Blocks() as demo:
    progress_html = gr.HTML("<div id='custom-progress'></div>", visible=False)
    chat = gr.ChatInterface(...)

    # Update progress_html separately from chat
```

**Pros**:
- Full control over positioning
- Can match exact design requirements

**Cons**:
- Significant refactor required
- May break MCP server integration
- More moving parts = more bugs

### Option 4: Hybrid - Progress in `additional_inputs_accordion`

Place a separate `gr.Progress` component in a fixed position (e.g., accordion header):

```python
with gr.Blocks() as demo:
    with gr.Row():
        progress_bar = gr.Slider(0, 100, value=0, label="Progress", interactive=False)
    chat = gr.ChatInterface(...)
```

**Pros**:
- Fixed position, no overlap

**Cons**:
- Requires `gr.Blocks` wrapper (breaks MCP?)
- Clunky UX

## Recommended Fix

**Option 1: Remove `gr.Progress()`, keep emoji status text**

Rationale:
1. Our emoji status updates (`⏱️ **PROGRESS**: Round 2/5`) already provide the information
2. `gr.Progress()` was never designed for ChatInterface
3. Removing it eliminates the positioning conflict entirely
4. ChatInterface's built-in `show_progress="minimal"` handles the spinner

## Implementation Plan

1. **Remove** `progress: gr.Progress = gr.Progress()` parameter from `research_agent()`
2. **Remove** all `progress(...)` calls in the function
3. **Keep** emoji status yields (`⏱️ **PROGRESS**: ...`)
4. **Optionally** add `show_progress="minimal"` to ChatInterface (already default)
5. **Test** on HuggingFace Spaces

## Testing

```bash
# Local test
uv run python -c "from src.app import create_demo; demo, _ = create_demo(); demo.launch()"

# Verify:
# 1. No floating progress bar
# 2. Emoji status updates visible in chat
# 3. ChatInterface spinner works as expected
```

## References

- [Gradio Progress Bars Guide](https://www.gradio.app/guides/progress-bars)
- [Gradio ChatInterface Docs](https://www.gradio.app/docs/gradio/chatinterface)
- [GitHub Issue #5967: Progress bar for ChatInterface](https://github.com/gradio-app/gradio/issues/5967)
- [GitHub Issue #5815: Customize the progress bar](https://github.com/gradio-app/gradio/issues/5815)

## Version Info

- Gradio: `>=6.0.0` (pyproject.toml constraint)
- ChatInterface: Streaming async generator mode
- MCP Server: Enabled