Spaces:
Runtime error
Runtime error
HF Spaces Deployment Added
Browse files- .dockerignore +22 -0
- .github/workflows/docker-build.yml +95 -0
- Dockerfile +35 -0
- README.md +213 -1
- WORKFLOW_DIAGRAM.png +0 -0
- app.py +10 -0
- backend/__pycache__/voice_bot_controller.cpython-311.pyc +0 -0
- data/latency_results.json +136 -0
- docker-compose.yml +81 -0
- export_workflow_diagram.py +70 -0
- frontend/pages/workflow_diagram.py +77 -0
- orchestration/__pycache__/langgraph_workflow.cpython-311.pyc +0 -0
- orchestration/nodes/__pycache__/context_builder.cpython-311.pyc +0 -0
- orchestration/nodes/__pycache__/entity_extraction.cpython-311.pyc +0 -0
- orchestration/nodes/__pycache__/intent_detection.cpython-311.pyc +0 -0
- orchestration/nodes/__pycache__/memory_persistence.cpython-311.pyc +0 -0
- orchestration/nodes/__pycache__/response_generation.cpython-311.pyc +0 -0
- orchestration/nodes/__pycache__/retrieval_router.cpython-311.pyc +0 -0
- orchestration/nodes/__pycache__/sentiment_hybrid.cpython-311.pyc +0 -0
- orchestration/nodes/__pycache__/tts_generation.cpython-311.pyc +0 -0
- orchestration/nodes/__pycache__/validation.cpython-311.pyc +0 -0
- spaces.yaml +10 -0
.dockerignore
ADDED
|
@@ -0,0 +1,22 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 1 |
+
venv/
|
| 2 |
+
__pycache__/
|
| 3 |
+
.pytest_cache/
|
| 4 |
+
.git/
|
| 5 |
+
.gitignore
|
| 6 |
+
.env
|
| 7 |
+
*.pyc
|
| 8 |
+
*.pyo
|
| 9 |
+
*.pyd
|
| 10 |
+
.DS_Store
|
| 11 |
+
node_modules/
|
| 12 |
+
dist/
|
| 13 |
+
build/
|
| 14 |
+
*.egg-info/
|
| 15 |
+
.vscode/
|
| 16 |
+
.idea/
|
| 17 |
+
.coverage
|
| 18 |
+
htmlcov/
|
| 19 |
+
*.db
|
| 20 |
+
data/audio_output/
|
| 21 |
+
data/sessions.db
|
| 22 |
+
latency_results.json
|
.github/workflows/docker-build.yml
ADDED
|
@@ -0,0 +1,95 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 1 |
+
name: Build and Push Docker Image
|
| 2 |
+
|
| 3 |
+
on:
|
| 4 |
+
push:
|
| 5 |
+
branches:
|
| 6 |
+
- main
|
| 7 |
+
- develop
|
| 8 |
+
pull_request:
|
| 9 |
+
branches:
|
| 10 |
+
- main
|
| 11 |
+
|
| 12 |
+
env:
|
| 13 |
+
REGISTRY: ghcr.io
|
| 14 |
+
IMAGE_NAME: ${{ github.repository }}
|
| 15 |
+
|
| 16 |
+
jobs:
|
| 17 |
+
build-and-push:
|
| 18 |
+
runs-on: ubuntu-latest
|
| 19 |
+
permissions:
|
| 20 |
+
contents: read
|
| 21 |
+
packages: write
|
| 22 |
+
|
| 23 |
+
steps:
|
| 24 |
+
- name: Checkout repository
|
| 25 |
+
uses: actions/checkout@v4
|
| 26 |
+
|
| 27 |
+
- name: Set up Docker Buildx
|
| 28 |
+
uses: docker/setup-buildx-action@v3
|
| 29 |
+
|
| 30 |
+
- name: Log in to GitHub Container Registry
|
| 31 |
+
uses: docker/login-action@v3
|
| 32 |
+
with:
|
| 33 |
+
registry: ${{ env.REGISTRY }}
|
| 34 |
+
username: ${{ github.actor }}
|
| 35 |
+
password: ${{ secrets.GITHUB_TOKEN }}
|
| 36 |
+
|
| 37 |
+
- name: Extract metadata for Docker
|
| 38 |
+
id: meta
|
| 39 |
+
uses: docker/metadata-action@v5
|
| 40 |
+
with:
|
| 41 |
+
images: ${{ env.REGISTRY }}/${{ env.IMAGE_NAME }}
|
| 42 |
+
tags: |
|
| 43 |
+
type=ref,event=branch
|
| 44 |
+
type=ref,event=pr
|
| 45 |
+
type=semver,pattern={{version}}
|
| 46 |
+
type=semver,pattern={{major}}.{{minor}}
|
| 47 |
+
type=sha,prefix={{branch}}-
|
| 48 |
+
type=raw,value=latest,enable={{is_default_branch}}
|
| 49 |
+
|
| 50 |
+
- name: Build and push Docker image
|
| 51 |
+
uses: docker/build-push-action@v5
|
| 52 |
+
with:
|
| 53 |
+
context: .
|
| 54 |
+
push: ${{ github.event_name != 'pull_request' }}
|
| 55 |
+
tags: ${{ steps.meta.outputs.tags }}
|
| 56 |
+
labels: ${{ steps.meta.outputs.labels }}
|
| 57 |
+
cache-from: type=gha
|
| 58 |
+
cache-to: type=gha,mode=max
|
| 59 |
+
|
| 60 |
+
- name: Image digest
|
| 61 |
+
run: echo "Image pushed with digest: ${{ steps.build.outputs.digest }}"
|
| 62 |
+
|
| 63 |
+
deploy-to-hf-spaces:
|
| 64 |
+
needs: build-and-push
|
| 65 |
+
runs-on: ubuntu-latest
|
| 66 |
+
if: github.event_name == 'push' && github.ref == 'refs/heads/main'
|
| 67 |
+
|
| 68 |
+
steps:
|
| 69 |
+
- name: Checkout repository
|
| 70 |
+
uses: actions/checkout@v4
|
| 71 |
+
|
| 72 |
+
- name: Push to HuggingFace Spaces
|
| 73 |
+
run: |
|
| 74 |
+
git config --global credential.helper store
|
| 75 |
+
echo "https://${{ secrets.HF_USERNAME }}:${{ secrets.HF_TOKEN }}@huggingface.co" > ~/.git-credentials
|
| 76 |
+
|
| 77 |
+
git remote add spaces https://huggingface.co/spaces/${{ secrets.HF_SPACE_REPO }}.git || true
|
| 78 |
+
git push --force spaces main
|
| 79 |
+
env:
|
| 80 |
+
HF_USERNAME: ${{ secrets.HF_USERNAME }}
|
| 81 |
+
HF_TOKEN: ${{ secrets.HF_TOKEN }}
|
| 82 |
+
|
| 83 |
+
notify:
|
| 84 |
+
needs: [build-and-push]
|
| 85 |
+
runs-on: ubuntu-latest
|
| 86 |
+
if: always()
|
| 87 |
+
|
| 88 |
+
steps:
|
| 89 |
+
- name: Build status
|
| 90 |
+
run: |
|
| 91 |
+
if [ "${{ needs.build-and-push.result }}" = "success" ]; then
|
| 92 |
+
echo "β
Docker image built and pushed successfully!"
|
| 93 |
+
else
|
| 94 |
+
echo "β Docker build failed"
|
| 95 |
+
fi
|
Dockerfile
ADDED
|
@@ -0,0 +1,35 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 1 |
+
# Voice RAG Bot - Multi-stage Dockerfile
|
| 2 |
+
|
| 3 |
+
FROM python:3.11-slim as base
|
| 4 |
+
|
| 5 |
+
WORKDIR /app
|
| 6 |
+
|
| 7 |
+
# Install system dependencies
|
| 8 |
+
RUN apt-get update && apt-get install -y \
|
| 9 |
+
ffmpeg \
|
| 10 |
+
libsndfile1 \
|
| 11 |
+
&& rm -rf /var/lib/apt/lists/*
|
| 12 |
+
|
| 13 |
+
# Copy requirements
|
| 14 |
+
COPY requirements.txt .
|
| 15 |
+
|
| 16 |
+
# Install Python dependencies
|
| 17 |
+
RUN pip install --no-cache-dir -r requirements.txt
|
| 18 |
+
|
| 19 |
+
# Copy project files
|
| 20 |
+
COPY . .
|
| 21 |
+
|
| 22 |
+
# Expose ports
|
| 23 |
+
# 8000 = FastAPI backend
|
| 24 |
+
# 8501 = Streamlit frontend
|
| 25 |
+
EXPOSE 8000 8501
|
| 26 |
+
|
| 27 |
+
# Create startup script
|
| 28 |
+
RUN echo '#!/bin/bash\n\
|
| 29 |
+
if [ "$APP_TYPE" = "backend" ]; then\n\
|
| 30 |
+
uvicorn backend.main:app --host 0.0.0.0 --port 8000\n\
|
| 31 |
+
else\n\
|
| 32 |
+
streamlit run frontend/streamlit_app.py --server.port 8501 --server.address 0.0.0.0\n\
|
| 33 |
+
fi' > /app/start.sh && chmod +x /app/start.sh
|
| 34 |
+
|
| 35 |
+
CMD ["/app/start.sh"]
|
README.md
CHANGED
|
@@ -58,7 +58,219 @@ streamlit run frontend/streamlit_app.py
|
|
| 58 |
|
| 59 |
---
|
| 60 |
|
| 61 |
-
##
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 62 |
|
| 63 |
### Via Streamlit Frontend (Recommended)
|
| 64 |
|
|
|
|
| 58 |
|
| 59 |
---
|
| 60 |
|
| 61 |
+
## οΏ½ Docker Deployment
|
| 62 |
+
|
| 63 |
+
### Option A: Docker Compose (Recommended for Development)
|
| 64 |
+
|
| 65 |
+
Start all services (Backend + Frontend + Qdrant + Redis):
|
| 66 |
+
```bash
|
| 67 |
+
docker-compose up -d
|
| 68 |
+
```
|
| 69 |
+
|
| 70 |
+
**Access Points:**
|
| 71 |
+
- π€ Frontend: http://localhost:8501
|
| 72 |
+
- βοΈ Backend: http://localhost:8000
|
| 73 |
+
- π Qdrant: http://localhost:6333
|
| 74 |
+
- πΎ Redis: localhost:6379
|
| 75 |
+
|
| 76 |
+
**Stop Services:**
|
| 77 |
+
```bash
|
| 78 |
+
docker-compose down
|
| 79 |
+
```
|
| 80 |
+
|
| 81 |
+
### Option B: Individual Docker Images
|
| 82 |
+
|
| 83 |
+
**Build Image:**
|
| 84 |
+
```bash
|
| 85 |
+
docker build -t voice-rag-bot:latest .
|
| 86 |
+
```
|
| 87 |
+
|
| 88 |
+
**Run Backend:**
|
| 89 |
+
```bash
|
| 90 |
+
docker run -p 8000:8000 \
|
| 91 |
+
-e APP_TYPE=backend \
|
| 92 |
+
-e GROQ_API_KEY=your_key \
|
| 93 |
+
-e QDRANT_URL=http://localhost:6333 \
|
| 94 |
+
voice-rag-bot:latest
|
| 95 |
+
```
|
| 96 |
+
|
| 97 |
+
**Run Frontend:**
|
| 98 |
+
```bash
|
| 99 |
+
docker run -p 8501:8501 \
|
| 100 |
+
-e APP_TYPE=frontend \
|
| 101 |
+
-e GROQ_API_KEY=your_key \
|
| 102 |
+
-e QDRANT_URL=http://localhost:6333 \
|
| 103 |
+
voice-rag-bot:latest
|
| 104 |
+
```
|
| 105 |
+
|
| 106 |
+
---
|
| 107 |
+
|
| 108 |
+
## π GitHub Actions CI/CD
|
| 109 |
+
|
| 110 |
+
### Setup GitHub Secrets
|
| 111 |
+
|
| 112 |
+
Add these secrets to your GitHub repository (Settings β Secrets and Variables β Actions):
|
| 113 |
+
|
| 114 |
+
| Secret Name | Value | Description |
|
| 115 |
+
|------------|-------|-------------|
|
| 116 |
+
| `GROQ_API_KEY` | `gsk_xxxxxxxxxxxx` | Groq API key for LLM |
|
| 117 |
+
| `HF_USERNAME` | `your_username` | HuggingFace username |
|
| 118 |
+
| `HF_TOKEN` | `hf_xxxxxxxxxxxx` | HuggingFace access token |
|
| 119 |
+
| `HF_SPACE_REPO` | `username/voice-rag-bot` | HF Spaces repo path |
|
| 120 |
+
|
| 121 |
+
**How to Add Secrets:**
|
| 122 |
+
1. Go to GitHub repository β Settings
|
| 123 |
+
2. Click "Secrets and variables" β "Actions"
|
| 124 |
+
3. Click "New repository secret"
|
| 125 |
+
4. Add each secret with name and value
|
| 126 |
+
|
| 127 |
+
### Automatic Deployment
|
| 128 |
+
|
| 129 |
+
The workflow (`.github/workflows/docker-build.yml`) automatically:
|
| 130 |
+
|
| 131 |
+
1. **On `main` branch push:**
|
| 132 |
+
- Builds Docker image
|
| 133 |
+
- Pushes to GitHub Container Registry (GHCR)
|
| 134 |
+
- Deploys to HuggingFace Spaces
|
| 135 |
+
- Generates tags: `main`, `latest`, `sha-xxxxx`
|
| 136 |
+
|
| 137 |
+
2. **On Pull Request:**
|
| 138 |
+
- Builds Docker image (no push)
|
| 139 |
+
- Validates Dockerfile syntax
|
| 140 |
+
- Tests image build
|
| 141 |
+
|
| 142 |
+
**Workflow File:**
|
| 143 |
+
- Location: `.github/workflows/docker-build.yml`
|
| 144 |
+
- Triggers: Push to `main`/`develop`, Pull requests
|
| 145 |
+
- Status: View in GitHub β Actions tab
|
| 146 |
+
|
| 147 |
+
**Access Docker Images:**
|
| 148 |
+
```bash
|
| 149 |
+
docker pull ghcr.io/your-username/voice-rag-bot:latest
|
| 150 |
+
docker pull ghcr.io/your-username/voice-rag-bot:main
|
| 151 |
+
```
|
| 152 |
+
|
| 153 |
+
---
|
| 154 |
+
|
| 155 |
+
## π€ HuggingFace Spaces Deployment
|
| 156 |
+
|
| 157 |
+
### Option A: Automatic Deployment (Via GitHub Actions)
|
| 158 |
+
|
| 159 |
+
1. Create HuggingFace Space: https://huggingface.co/spaces
|
| 160 |
+
- Name: `voice-rag-bot`
|
| 161 |
+
- License: OpenRAIL
|
| 162 |
+
- Private/Public: Your choice
|
| 163 |
+
|
| 164 |
+
2. Get HF credentials:
|
| 165 |
+
- Username: Your HF account name
|
| 166 |
+
- Token: https://huggingface.co/settings/tokens (create "write" token)
|
| 167 |
+
|
| 168 |
+
3. Add GitHub Secrets (see above):
|
| 169 |
+
- `HF_USERNAME`
|
| 170 |
+
- `HF_TOKEN`
|
| 171 |
+
- `HF_SPACE_REPO` = `username/voice-rag-bot`
|
| 172 |
+
|
| 173 |
+
4. **Push to main branch β Automatic deployment!**
|
| 174 |
+
|
| 175 |
+
### Option B: Manual Deployment to HF Spaces
|
| 176 |
+
|
| 177 |
+
1. **Create HF Space (if not exists):**
|
| 178 |
+
```bash
|
| 179 |
+
huggingface-cli repo create voice-rag-bot --type space --space-sdk streamlit
|
| 180 |
+
```
|
| 181 |
+
|
| 182 |
+
2. **Clone & Push:**
|
| 183 |
+
```bash
|
| 184 |
+
git clone https://huggingface.co/spaces/your-username/voice-rag-bot
|
| 185 |
+
cd voice-rag-bot
|
| 186 |
+
|
| 187 |
+
# Add your project files
|
| 188 |
+
cp -r /path/to/voice-rag-bot/* .
|
| 189 |
+
|
| 190 |
+
# Push to HF Spaces
|
| 191 |
+
git add .
|
| 192 |
+
git commit -m "Deploy Voice RAG Bot"
|
| 193 |
+
git push origin main
|
| 194 |
+
```
|
| 195 |
+
|
| 196 |
+
3. **Configure Secrets in HF Spaces:**
|
| 197 |
+
- Go to Space Settings β Variables and secrets
|
| 198 |
+
- Add: `GROQ_API_KEY`, `QDRANT_URL`, etc.
|
| 199 |
+
|
| 200 |
+
4. **App File:** `app.py` (automatically created)
|
| 201 |
+
|
| 202 |
+
### HF Spaces Configuration (`spaces.yaml`)
|
| 203 |
+
|
| 204 |
+
```yaml
|
| 205 |
+
title: Voice RAG Bot
|
| 206 |
+
description: Voice-enabled RAG chatbot
|
| 207 |
+
app_file: app.py
|
| 208 |
+
sdk: streamlit
|
| 209 |
+
sdk_version: "1.28.0"
|
| 210 |
+
python_version: "3.11"
|
| 211 |
+
cpu: true
|
| 212 |
+
gpu: true
|
| 213 |
+
startup_duration_timeout: 600
|
| 214 |
+
```
|
| 215 |
+
|
| 216 |
+
### HF Spaces Requirements
|
| 217 |
+
|
| 218 |
+
**Note:** HuggingFace Spaces runs Streamlit frontend only (no backend microservices).
|
| 219 |
+
|
| 220 |
+
**Options:**
|
| 221 |
+
1. **Use External Backend:**
|
| 222 |
+
- Deploy backend separately (Railway, Render, Heroku)
|
| 223 |
+
- Update `BACKEND_URL` in Streamlit config
|
| 224 |
+
- Spaces frontend connects to external backend
|
| 225 |
+
|
| 226 |
+
2. **Self-contained (Frontend Only):**
|
| 227 |
+
- Remove backend API calls
|
| 228 |
+
- Use Streamlit session state for data
|
| 229 |
+
- Limited functionality (no vector DB, LLM caching)
|
| 230 |
+
|
| 231 |
+
3. **Docker-based Space (Advanced):**
|
| 232 |
+
- Deploy full stack in Docker container
|
| 233 |
+
- Requires HF Spaces Docker runtime
|
| 234 |
+
- Use `Dockerfile` + `docker-compose.yml`
|
| 235 |
+
|
| 236 |
+
**Recommended:** Use external FastAPI backend on Render/Railway + Streamlit on HF Spaces
|
| 237 |
+
|
| 238 |
+
---
|
| 239 |
+
|
| 240 |
+
## π§ Environment Variables for Deployment
|
| 241 |
+
|
| 242 |
+
### Local Development
|
| 243 |
+
```
|
| 244 |
+
GROQ_API_KEY=gsk_xxxxxxxxxxxx
|
| 245 |
+
QDRANT_URL=http://localhost:6333
|
| 246 |
+
DEBUG=True
|
| 247 |
+
LOG_LEVEL=INFO
|
| 248 |
+
```
|
| 249 |
+
|
| 250 |
+
### Docker Compose
|
| 251 |
+
```
|
| 252 |
+
GROQ_API_KEY=gsk_xxxxxxxxxxxx
|
| 253 |
+
QDRANT_URL=http://qdrant:6333
|
| 254 |
+
BACKEND_URL=http://backend:8000
|
| 255 |
+
DEBUG=False
|
| 256 |
+
LOG_LEVEL=INFO
|
| 257 |
+
```
|
| 258 |
+
|
| 259 |
+
### HuggingFace Spaces
|
| 260 |
+
```
|
| 261 |
+
GROQ_API_KEY=gsk_xxxxxxxxxxxx
|
| 262 |
+
BACKEND_URL=https://your-backend-api.herokuapp.com
|
| 263 |
+
FRONTEND_MODE=SPACES
|
| 264 |
+
```
|
| 265 |
+
|
| 266 |
+
### GitHub Actions (Auto-set)
|
| 267 |
+
- `REGISTRY`: ghcr.io
|
| 268 |
+
- `IMAGE_NAME`: ${{ github.repository }}
|
| 269 |
+
- Secrets: See above
|
| 270 |
+
|
| 271 |
+
---
|
| 272 |
+
|
| 273 |
+
## οΏ½π Usage Guide
|
| 274 |
|
| 275 |
### Via Streamlit Frontend (Recommended)
|
| 276 |
|
WORKFLOW_DIAGRAM.png
ADDED
|
app.py
ADDED
|
@@ -0,0 +1,10 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 1 |
+
"""HuggingFace Spaces Entry Point - Streamlit Frontend"""
|
| 2 |
+
|
| 3 |
+
import sys
|
| 4 |
+
from pathlib import Path
|
| 5 |
+
|
| 6 |
+
# Add project root to path
|
| 7 |
+
sys.path.insert(0, str(Path(__file__).parent))
|
| 8 |
+
|
| 9 |
+
# Import and run the main Streamlit app
|
| 10 |
+
from frontend.streamlit_app import *
|
backend/__pycache__/voice_bot_controller.cpython-311.pyc
CHANGED
|
Binary files a/backend/__pycache__/voice_bot_controller.cpython-311.pyc and b/backend/__pycache__/voice_bot_controller.cpython-311.pyc differ
|
|
|
data/latency_results.json
CHANGED
|
@@ -138,5 +138,141 @@
|
|
| 138 |
"tts_generation": 16.6,
|
| 139 |
"workflow_orchestration": 50.1
|
| 140 |
}
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 141 |
}
|
| 142 |
]
|
|
|
|
| 138 |
"tts_generation": 16.6,
|
| 139 |
"workflow_orchestration": 50.1
|
| 140 |
}
|
| 141 |
+
},
|
| 142 |
+
{
|
| 143 |
+
"timestamp": "2026-06-03T18:29:39.252430",
|
| 144 |
+
"total_time_ms": 26031.32,
|
| 145 |
+
"modules": {
|
| 146 |
+
"sentiment_analysis": 0.0,
|
| 147 |
+
"entity_extraction": 2683.74,
|
| 148 |
+
"intent_detection": 2149.76,
|
| 149 |
+
"retrieval_router": 13606.48,
|
| 150 |
+
"context_builder": 0.0,
|
| 151 |
+
"response_generation": 1417.41,
|
| 152 |
+
"validation": 0.0,
|
| 153 |
+
"memory_persistence": 1065.74,
|
| 154 |
+
"tts_generation": 1723.5,
|
| 155 |
+
"workflow_orchestration": 26031.32
|
| 156 |
+
},
|
| 157 |
+
"breakdown_percent": {
|
| 158 |
+
"sentiment_analysis": 0.0,
|
| 159 |
+
"entity_extraction": 5.5,
|
| 160 |
+
"intent_detection": 4.4,
|
| 161 |
+
"retrieval_router": 28.0,
|
| 162 |
+
"context_builder": 0.0,
|
| 163 |
+
"response_generation": 2.9,
|
| 164 |
+
"validation": 0.0,
|
| 165 |
+
"memory_persistence": 2.2,
|
| 166 |
+
"tts_generation": 3.5,
|
| 167 |
+
"workflow_orchestration": 53.5
|
| 168 |
+
}
|
| 169 |
+
},
|
| 170 |
+
{
|
| 171 |
+
"timestamp": "2026-06-03T18:31:59.635819",
|
| 172 |
+
"total_time_ms": 7009.19,
|
| 173 |
+
"modules": {
|
| 174 |
+
"sentiment_analysis": 0.0,
|
| 175 |
+
"entity_extraction": 570.99,
|
| 176 |
+
"intent_detection": 1327.92,
|
| 177 |
+
"retrieval_router": 637.33,
|
| 178 |
+
"context_builder": 0.0,
|
| 179 |
+
"response_generation": 1209.4,
|
| 180 |
+
"validation": 0.0,
|
| 181 |
+
"memory_persistence": 1075.38,
|
| 182 |
+
"tts_generation": 2110.23,
|
| 183 |
+
"workflow_orchestration": 7009.19
|
| 184 |
+
},
|
| 185 |
+
"breakdown_percent": {
|
| 186 |
+
"sentiment_analysis": 0.0,
|
| 187 |
+
"entity_extraction": 4.1,
|
| 188 |
+
"intent_detection": 9.5,
|
| 189 |
+
"retrieval_router": 4.6,
|
| 190 |
+
"context_builder": 0.0,
|
| 191 |
+
"response_generation": 8.7,
|
| 192 |
+
"validation": 0.0,
|
| 193 |
+
"memory_persistence": 7.7,
|
| 194 |
+
"tts_generation": 15.1,
|
| 195 |
+
"workflow_orchestration": 50.3
|
| 196 |
+
}
|
| 197 |
+
},
|
| 198 |
+
{
|
| 199 |
+
"timestamp": "2026-06-03T18:32:31.131203",
|
| 200 |
+
"total_time_ms": 5959.28,
|
| 201 |
+
"modules": {
|
| 202 |
+
"sentiment_analysis": 0.0,
|
| 203 |
+
"entity_extraction": 123.39,
|
| 204 |
+
"intent_detection": 1338.2,
|
| 205 |
+
"retrieval_router": 298.56,
|
| 206 |
+
"context_builder": 0.0,
|
| 207 |
+
"response_generation": 1028.93,
|
| 208 |
+
"validation": 1.81,
|
| 209 |
+
"memory_persistence": 1062.51,
|
| 210 |
+
"tts_generation": 2081.34,
|
| 211 |
+
"workflow_orchestration": 5959.28
|
| 212 |
+
},
|
| 213 |
+
"breakdown_percent": {
|
| 214 |
+
"sentiment_analysis": 0.0,
|
| 215 |
+
"entity_extraction": 1.0,
|
| 216 |
+
"intent_detection": 11.3,
|
| 217 |
+
"retrieval_router": 2.5,
|
| 218 |
+
"context_builder": 0.0,
|
| 219 |
+
"response_generation": 8.7,
|
| 220 |
+
"validation": 0.0,
|
| 221 |
+
"memory_persistence": 8.9,
|
| 222 |
+
"tts_generation": 17.5,
|
| 223 |
+
"workflow_orchestration": 50.1
|
| 224 |
+
}
|
| 225 |
+
},
|
| 226 |
+
{
|
| 227 |
+
"timestamp": "2026-06-03T18:36:02.419370",
|
| 228 |
+
"total_time_ms": 20168.46,
|
| 229 |
+
"modules": {
|
| 230 |
+
"sentiment_analysis": 0.0,
|
| 231 |
+
"validation": 0.0,
|
| 232 |
+
"entity_extraction": 840.66,
|
| 233 |
+
"intent_detection": 1772.81,
|
| 234 |
+
"response_generation": 2562.12,
|
| 235 |
+
"retrieval_router": 2732.23,
|
| 236 |
+
"context_builder": 0.0,
|
| 237 |
+
"memory_persistence": 1871.22,
|
| 238 |
+
"tts_generation": 4072.96,
|
| 239 |
+
"workflow_orchestration": 20168.46
|
| 240 |
+
},
|
| 241 |
+
"breakdown_percent": {
|
| 242 |
+
"sentiment_analysis": 0.0,
|
| 243 |
+
"validation": 0.0,
|
| 244 |
+
"entity_extraction": 2.5,
|
| 245 |
+
"intent_detection": 5.2,
|
| 246 |
+
"response_generation": 7.5,
|
| 247 |
+
"retrieval_router": 8.0,
|
| 248 |
+
"context_builder": 0.0,
|
| 249 |
+
"memory_persistence": 5.5,
|
| 250 |
+
"tts_generation": 12.0,
|
| 251 |
+
"workflow_orchestration": 59.3
|
| 252 |
+
}
|
| 253 |
+
},
|
| 254 |
+
{
|
| 255 |
+
"timestamp": "2026-06-03T18:40:18.536003",
|
| 256 |
+
"total_time_ms": 421490.8,
|
| 257 |
+
"modules": {
|
| 258 |
+
"sentiment_analysis": 0.0,
|
| 259 |
+
"entity_extraction": 119.72,
|
| 260 |
+
"intent_detection": 978.72,
|
| 261 |
+
"retrieval_router": 307.16,
|
| 262 |
+
"context_builder": 0.0,
|
| 263 |
+
"response_generation": 3172.24,
|
| 264 |
+
"validation": 0.0,
|
| 265 |
+
"workflow_orchestration": 421487.38
|
| 266 |
+
},
|
| 267 |
+
"breakdown_percent": {
|
| 268 |
+
"sentiment_analysis": 0.0,
|
| 269 |
+
"entity_extraction": 0.0,
|
| 270 |
+
"intent_detection": 0.2,
|
| 271 |
+
"retrieval_router": 0.1,
|
| 272 |
+
"context_builder": 0.0,
|
| 273 |
+
"response_generation": 0.7,
|
| 274 |
+
"validation": 0.0,
|
| 275 |
+
"workflow_orchestration": 98.9
|
| 276 |
+
}
|
| 277 |
}
|
| 278 |
]
|
docker-compose.yml
ADDED
|
@@ -0,0 +1,81 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 1 |
+
version: '3.8'
|
| 2 |
+
|
| 3 |
+
services:
|
| 4 |
+
# Qdrant Vector Database
|
| 5 |
+
qdrant:
|
| 6 |
+
image: qdrant/qdrant:latest
|
| 7 |
+
ports:
|
| 8 |
+
- "6333:6333"
|
| 9 |
+
- "6334:6334"
|
| 10 |
+
volumes:
|
| 11 |
+
- qdrant_storage:/qdrant/storage
|
| 12 |
+
environment:
|
| 13 |
+
- QDRANT_API_KEY=${QDRANT_API_KEY:-}
|
| 14 |
+
networks:
|
| 15 |
+
- voice-rag-network
|
| 16 |
+
|
| 17 |
+
# FastAPI Backend
|
| 18 |
+
backend:
|
| 19 |
+
build:
|
| 20 |
+
context: .
|
| 21 |
+
dockerfile: Dockerfile
|
| 22 |
+
environment:
|
| 23 |
+
- APP_TYPE=backend
|
| 24 |
+
- GROQ_API_KEY=${GROQ_API_KEY}
|
| 25 |
+
- GROQ_MODEL=${GROQ_MODEL}
|
| 26 |
+
- QDRANT_URL=http://qdrant:6333
|
| 27 |
+
- QDRANT_API_KEY=${QDRANT_API_KEY:-}
|
| 28 |
+
- KB_COLLECTION=${KB_COLLECTION}
|
| 29 |
+
- HISTORY_COLLECTION=${HISTORY_COLLECTION}
|
| 30 |
+
- DEBUG=${DEBUG:-True}
|
| 31 |
+
- LOG_LEVEL=${LOG_LEVEL:-INFO}
|
| 32 |
+
ports:
|
| 33 |
+
- "8000:8000"
|
| 34 |
+
depends_on:
|
| 35 |
+
- qdrant
|
| 36 |
+
networks:
|
| 37 |
+
- voice-rag-network
|
| 38 |
+
volumes:
|
| 39 |
+
- ./data:/app/data
|
| 40 |
+
|
| 41 |
+
# Streamlit Frontend
|
| 42 |
+
frontend:
|
| 43 |
+
build:
|
| 44 |
+
context: .
|
| 45 |
+
dockerfile: Dockerfile
|
| 46 |
+
environment:
|
| 47 |
+
- APP_TYPE=frontend
|
| 48 |
+
- GROQ_API_KEY=${GROQ_API_KEY}
|
| 49 |
+
- GROQ_MODEL=${GROQ_MODEL}
|
| 50 |
+
- QDRANT_URL=http://qdrant:6333
|
| 51 |
+
- QDRANT_API_KEY=${QDRANT_API_KEY:-}
|
| 52 |
+
- KB_COLLECTION=${KB_COLLECTION}
|
| 53 |
+
- HISTORY_COLLECTION=${HISTORY_COLLECTION}
|
| 54 |
+
- DEBUG=${DEBUG:-True}
|
| 55 |
+
- LOG_LEVEL=${LOG_LEVEL:-INFO}
|
| 56 |
+
ports:
|
| 57 |
+
- "8501:8501"
|
| 58 |
+
depends_on:
|
| 59 |
+
- backend
|
| 60 |
+
networks:
|
| 61 |
+
- voice-rag-network
|
| 62 |
+
volumes:
|
| 63 |
+
- ./data:/app/data
|
| 64 |
+
|
| 65 |
+
# Redis Cache (Optional)
|
| 66 |
+
redis:
|
| 67 |
+
image: redis:7-alpine
|
| 68 |
+
ports:
|
| 69 |
+
- "6379:6379"
|
| 70 |
+
networks:
|
| 71 |
+
- voice-rag-network
|
| 72 |
+
volumes:
|
| 73 |
+
- redis_storage:/data
|
| 74 |
+
|
| 75 |
+
volumes:
|
| 76 |
+
qdrant_storage:
|
| 77 |
+
redis_storage:
|
| 78 |
+
|
| 79 |
+
networks:
|
| 80 |
+
voice-rag-network:
|
| 81 |
+
driver: bridge
|
export_workflow_diagram.py
ADDED
|
@@ -0,0 +1,70 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 1 |
+
#!/usr/bin/env python3
|
| 2 |
+
"""Export LangGraph workflow diagram"""
|
| 3 |
+
|
| 4 |
+
import sys
|
| 5 |
+
from pathlib import Path
|
| 6 |
+
|
| 7 |
+
sys.path.insert(0, str(Path(__file__).parent))
|
| 8 |
+
|
| 9 |
+
from orchestration.langgraph_workflow import get_workflow_graph, compiled_workflow
|
| 10 |
+
|
| 11 |
+
def save_mermaid_diagram():
|
| 12 |
+
"""Save Mermaid diagram to file"""
|
| 13 |
+
diagram = get_workflow_graph()
|
| 14 |
+
|
| 15 |
+
output_path = Path("WORKFLOW_DIAGRAM.md")
|
| 16 |
+
with open(output_path, "w") as f:
|
| 17 |
+
f.write("# Voice RAG Bot - LangGraph Workflow Diagram\n\n")
|
| 18 |
+
f.write("```mermaid\n")
|
| 19 |
+
f.write(diagram)
|
| 20 |
+
f.write("\n```\n")
|
| 21 |
+
|
| 22 |
+
print(f"β Mermaid diagram saved to {output_path}")
|
| 23 |
+
return diagram
|
| 24 |
+
|
| 25 |
+
def save_ascii_diagram():
|
| 26 |
+
"""Save ASCII diagram to file"""
|
| 27 |
+
ascii_graph = compiled_workflow.get_graph().draw_ascii()
|
| 28 |
+
|
| 29 |
+
output_path = Path("WORKFLOW_ASCII.txt")
|
| 30 |
+
with open(output_path, "w") as f:
|
| 31 |
+
f.write(ascii_graph)
|
| 32 |
+
|
| 33 |
+
print(f"β ASCII diagram saved to {output_path}")
|
| 34 |
+
return ascii_graph
|
| 35 |
+
|
| 36 |
+
def save_png_diagram():
|
| 37 |
+
"""Save PNG diagram to file"""
|
| 38 |
+
try:
|
| 39 |
+
png_bytes = compiled_workflow.get_graph().draw_mermaid_png()
|
| 40 |
+
|
| 41 |
+
output_path = Path("WORKFLOW_DIAGRAM.png")
|
| 42 |
+
with open(output_path, "wb") as f:
|
| 43 |
+
f.write(png_bytes)
|
| 44 |
+
|
| 45 |
+
print(f"β PNG diagram saved to {output_path} ({len(png_bytes)} bytes)")
|
| 46 |
+
return output_path
|
| 47 |
+
except Exception as e:
|
| 48 |
+
print(f"β PNG diagram generation failed: {e}")
|
| 49 |
+
print(" (Requires 'playwright' package: pip install playwright)")
|
| 50 |
+
return None
|
| 51 |
+
|
| 52 |
+
if __name__ == "__main__":
|
| 53 |
+
print("Exporting workflow diagrams...\n")
|
| 54 |
+
|
| 55 |
+
mermaid = save_mermaid_diagram()
|
| 56 |
+
print("\nMermaid Output:")
|
| 57 |
+
print("-" * 60)
|
| 58 |
+
print(mermaid[:500] + "..." if len(mermaid) > 500 else mermaid)
|
| 59 |
+
|
| 60 |
+
try:
|
| 61 |
+
ascii_diag = save_ascii_diagram()
|
| 62 |
+
print("\nASCII Output:")
|
| 63 |
+
print("-" * 60)
|
| 64 |
+
print(ascii_diag[:500] + "..." if len(ascii_diag) > 500 else ascii_diag)
|
| 65 |
+
except Exception as e:
|
| 66 |
+
print(f"\nβ ASCII diagram not available: {e}")
|
| 67 |
+
|
| 68 |
+
png_path = save_png_diagram()
|
| 69 |
+
|
| 70 |
+
print("\nβ Workflow diagrams exported successfully!")
|
frontend/pages/workflow_diagram.py
ADDED
|
@@ -0,0 +1,77 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 1 |
+
"""Streamlit page for workflow visualization"""
|
| 2 |
+
|
| 3 |
+
import streamlit as st
|
| 4 |
+
from pathlib import Path
|
| 5 |
+
import sys
|
| 6 |
+
|
| 7 |
+
sys.path.insert(0, str(Path(__file__).parent.parent))
|
| 8 |
+
|
| 9 |
+
from orchestration.langgraph_workflow import compiled_workflow
|
| 10 |
+
|
| 11 |
+
st.set_page_config(page_title="Workflow Diagram", layout="wide")
|
| 12 |
+
|
| 13 |
+
st.title("π LangGraph Workflow Diagram")
|
| 14 |
+
|
| 15 |
+
st.markdown("""
|
| 16 |
+
This page displays the 9-node orchestration pipeline for the Voice RAG Bot:
|
| 17 |
+
- **Nodes**: Sentiment Analysis β Entity Extraction β Intent Detection β Retrieval β Context β Response β Validation β Memory β TTS
|
| 18 |
+
- **Parallel Execution**: Sentiment & Entity steps run in parallel
|
| 19 |
+
- **Conditional Logic**: Validation node can retry response generation if quality checks fail
|
| 20 |
+
""")
|
| 21 |
+
|
| 22 |
+
try:
|
| 23 |
+
# Generate PNG diagram
|
| 24 |
+
png_bytes = compiled_workflow.get_graph().draw_mermaid_png()
|
| 25 |
+
|
| 26 |
+
col1, col2 = st.columns([2, 1])
|
| 27 |
+
|
| 28 |
+
with col1:
|
| 29 |
+
st.image(png_bytes, caption="Voice RAG Bot - 9-Node Workflow", use_column_width=True)
|
| 30 |
+
|
| 31 |
+
with col2:
|
| 32 |
+
st.subheader("Workflow Details")
|
| 33 |
+
|
| 34 |
+
details = """
|
| 35 |
+
**9 Nodes:**
|
| 36 |
+
1. Sentiment Analysis
|
| 37 |
+
2. Entity Extraction
|
| 38 |
+
3. Intent Detection
|
| 39 |
+
4. Retrieval Router
|
| 40 |
+
5. Context Builder
|
| 41 |
+
6. Response Generation
|
| 42 |
+
7. Validation
|
| 43 |
+
8. Memory Persistence
|
| 44 |
+
9. TTS Generation
|
| 45 |
+
|
| 46 |
+
**Features:**
|
| 47 |
+
- Parallel execution
|
| 48 |
+
- Conditional retries
|
| 49 |
+
- Latency tracking
|
| 50 |
+
- Audio generation
|
| 51 |
+
"""
|
| 52 |
+
st.markdown(details)
|
| 53 |
+
|
| 54 |
+
if st.button("π₯ Download Diagram as PNG"):
|
| 55 |
+
st.download_button(
|
| 56 |
+
label="Download PNG",
|
| 57 |
+
data=png_bytes,
|
| 58 |
+
file_name="workflow_diagram.png",
|
| 59 |
+
mime="image/png"
|
| 60 |
+
)
|
| 61 |
+
st.success("β PNG ready for download!")
|
| 62 |
+
|
| 63 |
+
except Exception as e:
|
| 64 |
+
st.error(f"β Error generating diagram: {e}")
|
| 65 |
+
st.info("π‘ Make sure playwright is installed: `pip install playwright`")
|
| 66 |
+
|
| 67 |
+
st.divider()
|
| 68 |
+
|
| 69 |
+
try:
|
| 70 |
+
# Display Mermaid text version as fallback
|
| 71 |
+
mermaid_text = compiled_workflow.get_graph().draw_mermaid()
|
| 72 |
+
|
| 73 |
+
with st.expander("π View Mermaid Source"):
|
| 74 |
+
st.code(mermaid_text, language="mermaid")
|
| 75 |
+
|
| 76 |
+
except Exception as e:
|
| 77 |
+
st.warning(f"Could not generate Mermaid source: {e}")
|
orchestration/__pycache__/langgraph_workflow.cpython-311.pyc
CHANGED
|
Binary files a/orchestration/__pycache__/langgraph_workflow.cpython-311.pyc and b/orchestration/__pycache__/langgraph_workflow.cpython-311.pyc differ
|
|
|
orchestration/nodes/__pycache__/context_builder.cpython-311.pyc
CHANGED
|
Binary files a/orchestration/nodes/__pycache__/context_builder.cpython-311.pyc and b/orchestration/nodes/__pycache__/context_builder.cpython-311.pyc differ
|
|
|
orchestration/nodes/__pycache__/entity_extraction.cpython-311.pyc
CHANGED
|
Binary files a/orchestration/nodes/__pycache__/entity_extraction.cpython-311.pyc and b/orchestration/nodes/__pycache__/entity_extraction.cpython-311.pyc differ
|
|
|
orchestration/nodes/__pycache__/intent_detection.cpython-311.pyc
CHANGED
|
Binary files a/orchestration/nodes/__pycache__/intent_detection.cpython-311.pyc and b/orchestration/nodes/__pycache__/intent_detection.cpython-311.pyc differ
|
|
|
orchestration/nodes/__pycache__/memory_persistence.cpython-311.pyc
CHANGED
|
Binary files a/orchestration/nodes/__pycache__/memory_persistence.cpython-311.pyc and b/orchestration/nodes/__pycache__/memory_persistence.cpython-311.pyc differ
|
|
|
orchestration/nodes/__pycache__/response_generation.cpython-311.pyc
CHANGED
|
Binary files a/orchestration/nodes/__pycache__/response_generation.cpython-311.pyc and b/orchestration/nodes/__pycache__/response_generation.cpython-311.pyc differ
|
|
|
orchestration/nodes/__pycache__/retrieval_router.cpython-311.pyc
CHANGED
|
Binary files a/orchestration/nodes/__pycache__/retrieval_router.cpython-311.pyc and b/orchestration/nodes/__pycache__/retrieval_router.cpython-311.pyc differ
|
|
|
orchestration/nodes/__pycache__/sentiment_hybrid.cpython-311.pyc
CHANGED
|
Binary files a/orchestration/nodes/__pycache__/sentiment_hybrid.cpython-311.pyc and b/orchestration/nodes/__pycache__/sentiment_hybrid.cpython-311.pyc differ
|
|
|
orchestration/nodes/__pycache__/tts_generation.cpython-311.pyc
CHANGED
|
Binary files a/orchestration/nodes/__pycache__/tts_generation.cpython-311.pyc and b/orchestration/nodes/__pycache__/tts_generation.cpython-311.pyc differ
|
|
|
orchestration/nodes/__pycache__/validation.cpython-311.pyc
CHANGED
|
Binary files a/orchestration/nodes/__pycache__/validation.cpython-311.pyc and b/orchestration/nodes/__pycache__/validation.cpython-311.pyc differ
|
|
|
spaces.yaml
ADDED
|
@@ -0,0 +1,10 @@
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
|
| 1 |
+
title: Voice RAG Bot
|
| 2 |
+
description: Voice-enabled RAG chatbot with sentiment analysis and entity extraction
|
| 3 |
+
app_file: app.py
|
| 4 |
+
sdk: streamlit
|
| 5 |
+
sdk_version: "1.28.0"
|
| 6 |
+
python_version: "3.11"
|
| 7 |
+
cpu: true
|
| 8 |
+
gpu: true
|
| 9 |
+
startup_duration_timeout: 600
|
| 10 |
+
hf_oauth: true
|