AI Observability

Çok Ajanlı RAG için Özel Enstrümantasyon Desenleri: OpenTelemetry ile İz Parçalanmasını Çözmek

Büyük Dil Modeli (LLM) uygulamaları basit soru-cevap botlarından karmaşık Çok Ajanlı Alıntı-Büyütme Üretimi (RAG) sistemlerine evrildikçe, gözlemlenebilirlik kritik bir darboğaza dönüşüyor. Tek ajanlı RAG kurulumunda istek doğrusal akar: sorgula, getir, üret. Ancak çok ajanlı mimarilerde istekler, her biri belge ayrıştırma, anlamsal arama veya gerçeklik doğrulama gibi farklı görevleri yerine getiren paralel alt ajanlara ayrılır. Bu karmaşıklık, tek bir kullanıcı isteğinin onlarca ilgisiz span'e yayıldığı iz parçalanmasına yol açar ve hata ayıklamayı neredeyse imkansız hale getirir.

Geleneksel günlük kaydı (logging), bağlam eksikliği nedeniyle yetersiz kalır. İşte burada OpenTelemetry (OTel) öne çıkar. Özel enstrümantasyon desenleri uygulayarak bu parçalanmış izleri bir araya getirebilir ve AI altyapınız için birleşik bir görünüm sağlayabilirsiniz. Bu yazıda, bu desenlerin Python kullanılarak nasıl yapılandırılacağını keşfedeceğiz.

Dağıtık AI İş Akışlarının Zorluğu

Üç ajanlı bir müşteri destek sistemini hayal edin: Bir Tashih (Triage) Ajanı, Bir Bilgi Getirme Ajanı ve Bir Yanıt Üretici. Bir kullanıcı sorgu gönderdiğinde, Tashih Ajanı niyeti belirler ve görevleri devreder. Eğer niyet teknikse, Bilgi Ajanı bir vektör veritabanında arama yapar; faturalandırma ile ilgiliyse bir SQL veritabanını sorgular.

Doğru korelasyon olmadan, bu ajanlar tarafından oluşturulan span'ler APM (Uygulama Performans İzleme) panelinizde izole adalar gibi görünür. Yanıt Üretici'deki yüksek gecikmenin, Bilgi Ajanının vektör aramasındaki bir zaman aşımından kaynaklandığını göremezsiniz. Bunu çözmek için bağlamı ajan sınırları boyunca açıkça yaymamız gerekir.

OpenTelemetry ile Özel Enstrümantasyon Uygulama

Temel strateji, her ajanın yürütme bağlamını yakalayan özel bir sarmalayıcı (wrapper) oluşturmaktan geçer. opentelemetry-api kullanarak span'leri manuel olarak yönetiriz ve böylece bir ajanın iç mantığındaki iç içe çağrılar, tek bir üst span altında gruplandırılır. Bu özellikle ajanlarınız LangChain, LlamaIndex veya otomatik enstrümantasyonu iyi olmayan özel HTTP istemcileri gibi birden fazla kütüphane kullandığında faydalıdır.

Aşağıda, tutarlı bir iz yapısı sağlamak için bir ajanın yürütme yöntemini saran özel bir dekoratörün pratik bir örneği yer almaktadır:

import functools
from opentelemetry import trace
from opentelemetry.trace import Status, StatusCode

tracer = trace.get_tracer(__name__)

def agent_span(agent_name: str):
    """
    Bir ajanın yöntemini özel bir OpenTelemetry span'i içinde saran bir dekoratör.
    """
    def decorator(func):
        @functools.wraps(func)
        def wrapper(*args, **kwargs):
            with tracer.start_as_current_span(f"agent.{agent_name}") as span:
                try:
                    # APM araçlarında daha iyi filtreleme için öznitelikler ayarla
                    span.set_attribute("agent.name", agent_name)
                    span.set_attribute("args", str(args)[:100]) # Girdileri temizle
                    
                    # Ajanın mantığını yürüt
                    result = func(*args, **kwargs)
                    
                    # Başarı işareti
                    span.set_status(Status(StatusCode.OK))
                    return result
                except Exception as e:
                    # Hata işareti ve hatayı kaydet
                    span.set_status(Status(StatusCode.ERROR, str(e)))
                    span.record_exception(e)
                    raise
        return wrapper
    return decorator

# Kullanım Örneği
class KnowledgeRetrievalAgent:
    @agent_span("knowledge_retrieval")
    def search_docs(self, query: str):
        # Pahalı bir vektör DB aramasını simüle et
        return {"doc_id": "123", "content": "Cevap 42'dir."}

Bu desende, @agent_span dekoratörü, o belirli ajan tarafından gerçekleştirilen tüm iç işlemler için bir kapsayıcı görevi görür. Birden fazla ajanı birbirine zincirlediğinizde, iç mantıktan gelen alt span'ler otomatik olarak ajanın span'i içine iç içe yerleştirilir; bu da olayların düz bir listesi yerine hiyerarşik bir görünüm oluşturur.

Hizmet Sınırları Across Span'leri Korelasyon

Mikro hizmetler olarak dağıtılan çok ajanlı sistemlerde bağlam yayılımı hayati önem taşır. TraceId ve SpanId'nin başlıklar (örneğin REST API'lerde HTTP başlıkları veya Kafka'da mesaj başlıkları) aracılığıyla geçirildiğinden emin olmalısınız. HTTP istemcinizin veya sunucu enstrümantasyonunuz etkinse OpenTelemetry'nin bağlam yayılımı yardımcı programları bunu otomatik olarak halleder. Ancak özel mesaj aracıları veya dahili olay barışıkları için bağlam taşıyıcısını manuel olarak enjekte etmeniz gerekebilir:

from opentelemetry.propagate import inject

def send_message_to_agent(queue, message, agent_name):
    # İz bağlamını mesaj meta verilerine enjekte et
    headers = {}
    inject(headers)
    
    queue.publish({
        "agent": agent_name,
        "payload": message,
        "trace_headers": headers
    })

Sonuç

Çok Ajanlı RAG sistemlerindeki iz parçalanmasını çözmek, sadece daha fazla veri toplamakla ilgili değildir; bu verileri zekice yapılandırmakla ilgilidir. OpenTelemetry ile özel enstrümantasyon desenleri benimseyerek geliştiriciler, ajan etkileşimlerinde granüler görünürlük elde edebilir, paralel iş akışları boyunca darboğazları belirleyebilir ve nihayetinde daha güvenilir AI uygulamaları oluşturabilir. Bu sistemler karmaşıklık kazandıkça, gözlemlenebilirlik isteğe bağlı bir özellikten operasyonel mükemmelliğin omurgasına dönüşecektir.

Share: