Local AI

ساخت یک پایپ‌لاین RAG محلی: یکپارچه‌سازی پایگاه‌های داده برداری با llama.cpp برای پرسش و پاسخ اسناد خصوصی

در عصری که حریم داده‌ها اولویت اصلی است، تکیه بر APIهای مدل‌های زبانی بزرگ شخص ثالث برای اطلاعات حساس، روز به روز غیرممکن‌تر می‌شود. توسعه‌دهندگان به سمت محیط‌های اجرای محلی روی می‌آورند که تضمین می‌کنند داده‌ها هرگز از دستگاه خارج نمی‌شوند. یکی از قدرتمندترین معماری‌ها برای این منظور، تولید تقویت‌شده با بازیابی (RAG) است که پاسخ‌های یک مدل زبانی بزرگ (LLM) را بر داده‌های خاص و متعلق به کاربر استوار می‌سازد. با ترکیب llama.cpp برای استنتاج محلی کارآمد با پایگاه‌های داده برداری قوی، می‌توانید یک سیستم پرسش و پاسخ اسناد امن، آفلاین و با دقت بالا بسازید.

درک معماری RAG محلی

یک پایپ‌لاین RAG سنتی شامل سه مرحله اصلی است: جذب، بازیابی و تولید. جذب شامل قطعه‌بندی اسناد و تبدیل آن‌ها به بردارهای چگال (Embeddings) است. بازیابی فضای برداری را برای یافتن مرتبط‌ترین قطعات جستجو می‌کند. در نهایت، تولید با استفاده از زمینه موجود در این قطعات، پاسخی را تدوین می‌کند. هنگام انجام این فرآیند به صورت محلی، چالش اصلی بهینه‌سازی برای محدودیت‌های سخت‌افزاری در حالی است که سرعت و دقت حفظ می‌شود. llama.cpp در اینجا با ارائه یک بک‌اند C++ که از شتاب‌دهنده سخت‌افزاری در CPUها و GPUها بهره می‌برد، درخشش می‌کند و دسترسی را حتی برای لپ‌تاپ‌های مصرفی ممکن می‌سازد.

راه‌اندازی محیط

برای شروع، به یک محیط پایتون مجهز به کتابخانه‌های ضروری نیاز دارید. ما از langchain برای ارکستراسیون پایپ‌لاین، chromadb برای ذخیره‌سازی برداری سبک و llama-cpp-python برای موتور استنتاج استفاده خواهیم کرد. مطمئن شوید که یک مدل GGUF کوانتیزه شده، مانند Llama-3-8B یا Mistral، را در دایرکتوری محلی خود دانلود کرده‌اید.

وابستگی‌ها را با استفاده از pip نصب کنید:


pip install langchain chromadb llama-cpp-python langchain-community sentence-transformers

پیاده‌سازی ذخیره‌سازی برداری

اولین مرحله در هر پایپ‌لاین RAG، پردازش متن ساختارنیافته است. ما باید اسناد را به قطعات تقسیم کرده و برای هر بخش امبدینگ (Embedding) تولید کنیم. LangChain این کار را با استفاده از تقسیم‌کننده‌های سند و مدل‌های امبدینگ آن ساده می‌کند. برای اجرای محلی، می‌توانیم از مدل‌های امبدینگ سبک استفاده کنیم که به طور کارآمد روی CPU اجرا می‌شوند.


from langchain.document_loaders import TextLoader
from langchain.text_splitter import RecursiveCharacterTextSplitter
from langchain.embeddings import HuggingFaceEmbeddings
from langchain.vectorstores import Chroma

# بارگذاری و تقسیم اسناد
loader = TextLoader("my_private_data.txt")
documents = loader.load()
text_splitter = RecursiveCharacterTextSplitter(chunk_size=500, chunk_overlap=50)
texts = text_splitter.split_documents(documents)

# راه‌اندازی امبدینگ‌های محلی
embeddings = HuggingFaceEmbeddings(model_name="sentence-transformers/all-MiniLM-L6-v2")

# ایجاد پایگاه داده برداری
db = Chroma.from_documents(texts, embeddings)

این کد یک نمونه محلی ChromaDB ایجاد می‌کند که داده‌ها را روی دیسک شما ذخیره می‌کند و حریم خصوصی کامل را تضمین می‌نماید. مدل all-MiniLM-L6-v2 به دلیل تعادل بین سرعت و دقت معنایی انتخاب شده است.

یکپارچه‌سازی llama.cpp برای تولید

با آماده بودن بازیاب، مدل زبانی را پیکربندی می‌کنیم. llama-cpp-python به ما اجازه می‌دهد مدل‌های GGUF را مستقیماً بارگذاری کنیم. ما باید یک قالب پرامپت (Prompt) تعریف کنیم که به مدل دستور دهد تنها از زمینه ارائه‌شده برای پاسخ به سوال استفاده کند تا از توهم‌زدایی (Hallucination) جلوگیری شود.


from langchain.llms import LlamaCpp
from langchain.chains import RetrievalQA
import os

# اشاره به مدل محلی GGUF شما
model_path = "./models/llama-3-8b-instruct.Q4_K_M.gguf"

llm = LlamaCpp(
    model_path=model_path,
    n_gpu_layers=-1,
    max_tokens=500,
    n_ctx=2048,
    temperature=0,
    verbose=True
)

# ایجاد زنجیره RAG
qa_chain = RetrievalQA.from_chain_type(
    llm=llm,
    chain_type="stuff",
    retriever=db.as_retriever(search_kwargs={"k": 2})
)

# پرسش از سیستم
response = qa_chain.run("What are the key security protocols mentioned in the text?")
print(response)

بهینه‌سازی و بهترین شیوه‌ها

هنگام اجرای RAG به صورت محلی، مدیریت حافظه حیاتی است. اگر با خطاهای کمبود حافظه (OOM) مواجه شدید، در نظر بگیرید که مدل‌های خود را بیشتر کوانتیزه کنید (مثلاً Q3_K_S) یا پارامتر n_ctx را کاهش دهید. علاوه بر این، تنظیم اندازه قطعات می‌تواند تأثیر قابل توجهی بر دقت بازیابی داشته باشد. اگر قطعات خیلی کوچک باشند، زمینه از دست می‌رود و اگر خیلی بزرگ باشند، امبدینگ خاصیت خود را از دست می‌دهد. آزمایش با اندازه‌های قطعه بین ۳۰۰ تا ۸۰۰ توکن نقطه شروع خوبی است.

نتیجه‌گیری

ساخت یک پایپ‌لاین RAG محلی با llama.cpp به توسعه‌دهندگان این امکان را می‌دهد تا از قابلیت‌های مدل‌های زبانی بزرگ بهره‌مند شوند بدون آنکه حاکمیت داده‌ها به خطر بیفتد. با یکپارچه‌سازی پایگاه‌های داده برداری مانند ChromaDB برای بازیابی کارآمد و بهره‌گیری از کارایی مدل‌های GGUF، شما سیستمی ایجاد می‌کنید که هم خصوصی و هم دارای عملکرد بالا است. با پیشرفت سخت‌افزار و پیچیده‌تر شدن مدل‌های هوش مصنوعی محلی، مانع ورود برای استقرار برنامه‌های هوشمند و امن تنها کاهش خواهد یافت. امروزه شروع به ساخت پایگاه دانش خصوصی خود کنید.

Share: