llm-chat-project / README.md
DunasAnastasiia
Fix Space YAML metadata
50b94ce
---
title: RAG QA (BM25 + Dense + Reranker)
emoji: 🔎
colorFrom: indigo
colorTo: pink
sdk: gradio
sdk_version: "6.1.0"
python_version: "3.10"
app_file: app.py
pinned: false
short_description: RAG QA demo BM25 + Dense + reranker
---
# RAG QA (BM25 + Dense + OpenAI-compatible providers)
Це навчальний проєкт **Retrieval-Augmented Generation (RAG)** для задачі **Question Answering**: система знаходить релевантні уривки в корпусі документів і відповідає на питання, спираючись лише на знайдений контекст. :contentReference[oaicite:2]{index=2}
## Demo
- Hugging Face Space: *(посилання після деплою)*
- GitHub: https://github.com/DunasAnastasiia/llm-chat-project
---
## Як працює система (архітектура)
**Джерело даних (Dataset)**
- Hugging Face dataset: `rag-datasets/rag-mini-wikipedia` :contentReference[oaicite:3]{index=3}
**Chunking**
- Простий character-based chunking з overlap: `chunk_chars=900`, `overlap_chars=150`
**Retriever**
- **BM25** (лексичний пошук по ключових словах)
- **Dense retrieval** (Sentence-Transformers embeddings)
- Можна **вмикати/вимикати** BM25 та Dense окремо (для порівняння якості).
**Reranker (optional)**
- Cross-encoder `cross-encoder/ms-marco-MiniLM-L-6-v2` для реранкінгу кандидатів (опціонально).
**LLM (Generation)**
- Використовується **OpenAI-compatible Chat Completions API** через бібліотеку `openai` із параметром `base_url`.
- Працює з провайдерами типу **Groq** / **OpenRouter** (ключ вводиться в UI).
**Citations**
- В промпті LLM проситься цитувати чанки як `[1] [2] ...`, а в UI показується список retrieved chunks з `source_id` / `chunk_id`.
**UI**
- Gradio (web app), тумблери `Use BM25 / Use Dense / Use Reranker`, поле для API key. :contentReference[oaicite:9]{index=9}
## Приклади запитів: де BM25 кращий, а де Dense
### Запити, де краще справляється BM25
**Q:** Was Abraham Lincoln the first President of the United States?
**Очікувана відповідь:** No
**Чому BM25 кращий:** запит містить дуже конкретні ключові слова (Abraham Lincoln, first President, United States). BM25 добре працює, коли відповідь лежить у чанку з тими самими словами/формулюванням.
**Q:** Who was the general in charge at the Battle of Antietam?
**Очікувана відповідь:** General McClellan
**Чому BM25 кращий:** тут є точні “якорі” (Battle of Antietam, general in charge). BM25 зазвичай підтягує уривок, де ці терміни зустрічаються буквально.
---
### Запити, де кращі результати повертає Dense retriever
**Q:** Who assassinated Lincoln?
**Очікувана відповідь:** John Wilkes Booth
**Чому dense кращий:** типовий приклад “семантичного” запиту — відповідь може бути в уривку, який не повторює точну форму запиту (наприклад, “Lincoln was assassinated by …”). Dense краще ловить перефразування й зв’язки “подія ↔ учасник”.
**Q:** What caused Calvin Jr.'s death?
**Очікувана відповідь:** heart attack
**Чому dense кращий:** питання може збігатися з текстом не дослівно (наприклад, у корпусі “died of a heart attack”). Dense часто краще дістає такі уривки навіть без точного збігу слів.
---
## Швидкий старт локально
### 1) Встановлення
```bash
python -m venv .venv
source .venv/bin/activate # Windows: .venv\Scripts\activate
pip install -r requirements.txt