OCR → RAG Integratsiyasi
OCR ning pipeline dagi o'rni
RAG qo'llanmasi 5-bobidagi ingestion pipeline ni eslang: scraping → extraction → chunking → embedding → pgvector. OCR bu zanjirga extraction bosqichida ulanadi:
Hujjat manbalari
|
+-- web sahifa -------> BeautifulSoup extractor --+
| |
+-- digital PDF -------> pdfplumber ---------------+--> TOZALASH --> chunking
| | (shu bob) |
+-- skanerlangan PDF --> OCR pipeline (7-bob) -----+ v
| | embedding
+-- rasm (jpg/png) ----> OCR to'g'ridan-to'g'ri ---+ |
v
pgvector
Lekin OCR matni to'g'ridan-to'g'ri chunking ga yuborilmaydi — avval tozalash kerak. Nega?
OCR matni nega "iflos"
Tesseract har vizual qatorni \n bilan tugatadi. Qog'ozda 60-belgilik qatorlar — demak har gap 2-3 bo'lakka bo'linadi:
OCR chiqishi: Bo'lishi kerak edi: Shartnoma tomonlari o'z zimma- Shartnoma tomonlari o'z siga olgan majburiyatlarni to'- zimmasiga olgan majburiyatlarni liq bajarishga kafolat beradi. to'liq bajarishga kafolat beradi.
RAG qo'llanmasi 4-bobini eslang: paragraph-based chunking paragraf chegaralariga (\n\n) tayanadi. OCR matni esa har 60 belgida \n — chunker "har qator alohida paragraf" deb o'ylaydi va chunk lar mayda-mayda bo'lib ketadi. Embedding sifati ham tushadi: "zimma-" va "siga" alohida so'zlar emas.
Tozalash funksiyasi
To'rt eng muhim tuzatish:
import re def clean_ocr_text(text): # 1. Bo'g'in ko'chirish: "zimma-\nsiga" -> "zimmasiga" text = re.sub(r"([\w'])-\n(\w)", r"\1\2", text) # 2. Sun'iy qator uzilishi: bitta \n -> bo'shliq # (\n\n paragraf chegarasi sifatida SAQLANADI) text = re.sub(r"(?<!\n)\n(?!\n)", " ", text) # 3. Ortiqcha bo'shliqlar text = re.sub(r"[ \t]{2,}", " ", text) # 4. Yolg'iz sahifa raqamlari va kolontitullar text = re.sub(r"^\s*-?\s*\d+\s*-?\s*$", "", text, flags=re.MULTILINE) return text.strip()
2-qadam eng nozigi: (?<!\n)\n(?!\n) — "oldida ham, orqasida ham \n bo'lmagan \n". Ya'ni yolg'iz qator uzilishi bo'shliqqa aylanadi, \n\n (haqiqiy paragraf) esa tegilmaydi.
Yana bir tez-tez uchraydigan muammo — har sahifada takrorlanadigan kolontitul ("«Nihol» MChJ — Ichki hujjat — Maxfiy"). U har chunk ga kirib, qidiruv natijalarini ifloslaydi. Yechim: sahifalar orasida takrorlangan qatorlarni topib olib tashlash (10-bobdagi kodda bor).
Metadata enrichment
RAG qo'llanmasi 4-bobidagi metadata g'oyasini OCR ma'lumoti bilan boyitamiz:
chunk_metadata = { "source_file": "shartnoma_2024.pdf", "page": 3, "extraction_method": "ocr_tesseract", # "text_layer" | "ocr_tesseract" | "ocr_vlm" "ocr_confidence": 84.2, # VLM uchun -1 (confidence bermaydi) "language": "rus", }
Bu metadata uch joyda asqotadi:
- Error analysis (RAG guide, 15-bob): foydalanuvchi "javob noto'g'ri" desa —
extraction_methodvaocr_confidencega qarang. Ko'pincha muammo retrieval da emas, manba matnning o'zida. - Filtering: "faqat ishonchli manbalardan javob ber" —
ocr_confidence > 70sharti bilan SQL darajasida filtrlash. - Citation: javob manbasini ko'rsatganda "skanerlangan hujjatdan olindi, xato bo'lishi mumkin" ogohlantirishi.
Quality gate — sifat darvozasi
Production tizimda past sifatli OCR ni jimgina bazaga qo'shib yubormaslik kerak. RAGAS (RAG guide, 10-bob) faqat retrieval/generation ni baholaydi — u manba matni buzuqligini ko'rmaydi. Darvoza shunday:
def quality_gate(page_result): if page_result.method == "text_layer": return "accept" # digital matn — ishonchli if page_result.method == "ocr_vlm": return "accept_with_flag" # confidence yo'q — belgilab qo'yamiz (6-bob: xatosi ko'rinmaydi) if page_result.confidence >= 80: return "accept" if page_result.confidence >= 60: return "accept_with_flag" # metadata da belgi, keyin tekshiriladi return "manual_review" # bazaga kirmasin, admin ko'rsin
Admin panelda "manual review" ro'yxati bo'ladi: past confidence li sahifalar odamga ko'rsatiladi. Odam yo qo'lda tuzatadi, yo qayta skanerlashni so'raydi, yo VLM natijasini tasdiqlaydi. Buzuq matn bazaga kirsa, uni topish juda qiyin — darvozada ushlash arzonroq. VLM o'qigan sahifalar ham har doim belgilanadi: ularda confidence yo'q, xatosi esa ko'rinmaydi (6-bob) — yuridik va moliyaviy hujjatlarda ularni odam ko'rib chiqadi.
Xulosa
| Tushuncha | Asosiy fikr |
|---|---|
| O'rin | OCR = extraction bosqichi; undan keyin har doim tozalash |
| Tozalash | Bo'g'in ko'chirish + yolg'iz \n — busiz chunking buziladi |
| Kolontitul | Takrorlangan qatorlarni olib tashlang — chunk larni ifloslaydi |
| Metadata | extraction_method + ocr_confidence — error analysis va filtering uchun |
| Quality gate | conf < 60 bazaga kirmasin — darvozada ushlash keyin qidirishdan arzon |
Bu bobni bepul o'qidingiz.
Kitob o'rgatadi, lekin sizning kodingiz nega ishlamaganini ayta olmaydi. Kursda uy vazifangiz tekshiriladi.