AI ответы по базе знаний

Задача: AI бот для ответов на вопросы в рамках предоставленных документов.

Решение: Dify как бекенд для создания базы знаний и бота, Open WEBUI для работы с ботом.

Нам понадобится

Dify — платформа для построения RAG-бота. Оркестрирует весь pipeline: chunking, embedding, retrieval, генерация ответа. Твой основной инструмент.

Open WebUI — веб-интерфейс для общения с моделями. Альтернативный фронтенд, если нужен более простой чат без workflow. В твоём случае Dify закрывает эту задачу, Open WebUI избыточен.

OpenAI API — используется для embedding (text-embedding-3-large), Summary Auto-Gen (gpt-5.4-mini), и генерации ответов (gpt-4o-mini). Основной платный ресурс.

Cohere API — используется только для reranker (rerank-multilingual-v3.0). Улучшает качество поиска, переранжируя найденные чанки перед передачей в LLM.

Настройка базы знаний

После деплоя и базовой настройки Dify приступаем к подготовке базы документов:
— все документы в PDF
— из всех документов нужно удалить содержание, обложки, оформление

Грузим документы с настройками:

Delimiter \n\n — режет текст по двойному переносу строки (между абзацами).

Maximum chunk length 2000 — максимальный размер одного чанка в символах.

Chunk overlap 200 — 200 символов из конца предыдущего чанка повторяются в начале следующего, чтобы не терять контекст на границах.

Replace consecutive spaces/newlines — убирает лишние пробелы и переносы, чистит текст перед индексацией.

Delete all URLs and email addresses — удаляет ссылки и email из текста (для BIM лучше отключить).

Summary Auto-Gen — отключён, генерация суммари для каждого чанка через LLM не выполняется.

High Quality — использует embedding модель для векторизации, обеспечивает точный семантический поиск.

text-embedding-3-large — модель для векторизации текста, преобразует чанки и запросы в векторы для семантического поиска.

Hybrid Search — одновременно выполняет векторный поиск (по смыслу) и полнотекстовый (по ключевым словам), затем объединяет результаты.

Rerank Model — после поиска переранжирует найденные чанки по релевантности к запросу.

rerank-multilingual-v3.0 — модель Cohere для переранжирования, поддерживает русский язык.

Top K 8 — возвращает 8 наиболее релевантных чанков для передачи в LLM.

Score Threshold 0.5 — отключён (toggle выключен), порог релевантности не применяется, возвращаются все Top K результаты.

Настройка бота

Создаем бота на основе шаблона «Knowledge Retrieval + ChatbotChatflow»

Knowledge Retrieval

INPUT+KNOW PROCESSING

Настройка модели

Системный промпт

{{#sys.dialogue_count#}}
{{#sys.conversation_id#}}
{{#sys.user_id#}}
{{#sys.app_id#}}
{{#sys.workflow_id#}}
{{#sys.workflow_run_id#}}
Ты умный помощник BIM менеджера. У тебя есть доступ к базе BIM документов — стандартам, регламентам, EIR, BEP.

Отвечай как опытный BIM эксперт:
- Помни историю разговора и отвечай в контексте беседы
- Используй предоставленный контекст из базы документов как основной источник
- Если контекст содержит релевантную информацию — отвечай на её основе подробно и структурированно
- Если контекст не содержит ответа — скажи "В базе документов эта информация не найдена" и предложи переформулировать вопрос
- Отвечай на том же языке что и вопрос
- Не упоминай названия конкретных компаний-заказчиков и их контакты
- Используй списки и заголовки для структурирования ответов
- При ответе указывай из какого документа взята информация

Контекст из базы документов:
{{#context#}}

Остальные настройки по умолчанию.

Все готово. Теперь можно публиковать бот и получать его API для Open WEBUI.

Open WEBUI

Код функции:

from pydantic import BaseModel
import requests
import json


class Pipe:
    class Valves(BaseModel):
        DIFY_API_KEY: str = ""
        DIFY_BASE_URL: str = "https://rag.avro.pro/v1"

    def __init__(self):
        self.valves = self.Valves()
        self.id = "avro-rag"
        self.name = "AVRO RAG Bot"

    def pipe(self, body: dict, __user__: dict = {}):
        # Берём последнее сообщение пользователя
        messages = body.get("messages", [])
        query = ""
        for m in reversed(messages):
            if m.get("role") == "user":
                query = m.get("content", "")
                break

        user_id = __user__.get("id", "openwebui-user")

        payload = {
            "inputs": {},
            "query": query,
            "response_mode": "streaming",
            "conversation_id": "",
            "user": user_id,
        }

        headers = {
            "Authorization": f"Bearer {self.valves.DIFY_API_KEY}",
            "Content-Type": "application/json",
        }

        response = requests.post(
            f"{self.valves.DIFY_BASE_URL}/chat-messages",
            headers=headers,
            json=payload,
            stream=True,
        )

        for line in response.iter_lines():
            if line:
                line = line.decode("utf-8")
                if line.startswith("data: "):
                    data = line[6:]
                    if data == "[DONE]":
                        break
                    try:
                        chunk = json.loads(data)
                        if chunk.get("event") == "message":
                            yield chunk.get("answer", "")
                    except Exception:
                        continue

После добавления указываем Dify Api Key + Dify Base Url. После этого наш бот появляется как новая доступная модель в Open WEBUI.

Можно работать!