• בלוג
  • יום 4 - בואו נכתוב סוכן שיחה

יום 4 - בואו נכתוב סוכן שיחה

03/10/2025

אתמול ראינו איך לכתוב תהליך עבודה שמורכב ממספר "סוכנים", כל אחד אחראי לחלק אחר של המשימה. היום נדבר על סוג שני של מערכות משולבות AI שהוא מערכות מבוססות שיחה. במערכות כאלה אין משימה ספציפית שצריך לבצע אלא אנחנו מגיעים לסוכן, שולחים הודעה והסוכן עונה או מבצע ואז מקשיב להמשך השיחה.

דוגמאות למערכות כאלה יכולות להיות:

  1. ממשק צ'ט עם סוכן חכם כמו באתר ChatGPT.

  2. סוכן תמיכה חכם שעונה לפניות של משתמשים במקום נציג אנושי.

  3. סוכן מכירות חכם שמתקשר למשתמש ומנהל שיחה כדי למכור מוצר.

  4. מורה לאנגלית שמנהל עם משתמש שיעור אנגלית מובנה תוך כדי שיחה.

1. לפני הכל - קוד

נתחיל בדוגמת קוד לשיחה עם סוכן חכם משורת הפקודה:

import asyncio

from agents import Agent, Runner, SQLiteSession

async def main():
    agent = Agent(name="Assistant", instructions="Reply very concisely.")

    # Create session instance
    session = SQLiteSession("conversation_123")

    while True:
        user_message = input("> ")
        ai_response = await Runner.run(agent, user_message, session=session)
        print(ai_response.final_output)


if __name__ == '__main__':
    asyncio.run(main())

הריצו את הקוד עם משתנה הסביבה OPENAI_API_KEY מכוון למפתח ה API שלכם ותקבלו שיחה עם סוכן חכם.

2. איך זה עובד

שורת הקסם בתוכנית היא:

ai_response = await Runner.run(agent, user_message, session=session)

ממשק העבודה עם LLM הוא Stateless, כלומר כל הודעה ל ChatGPT או לכל AI שנבחר מתחילה מאפס. בממשק של סוכן אנחנו רגילים שהסוכן ממשיך את השיחה ובשביל זה הוא צריך להתבסס על ההודעות הישנות. ניהול ההודעות הישנות ושליחתן יחד עם ההודעה החדשה מבוצע בצד הלקוח ובספריית openai-agents זה מנוהל באמצעות מנגנון ה session.

כדי להבין את המנגנון בואו נכתוב את הקוד בלי session:

import asyncio

from agents import Agent, Runner, SQLiteSession

async def main():
    agent = Agent(name="Assistant", instructions="Reply very concisely.")
    user_message = input("> ")
    result = await Runner.run(agent, user_message)
    print(result.final_output)

    while True:
        print(f"Debug: messages = {result.to_input_list()}")
        user_message = input("> ")
        result = await Runner.run(agent, result.to_input_list() + [{"role": "user", "content": user_message}])
        print(result.final_output)


if __name__ == '__main__':
    asyncio.run(main())

עכשיו זה ברור:

  1. ממשק Runner.run יכול לקבל הודעה בודדת או רשימה של הודעות.

  2. הממשק מחזיר אוביקט שמכיל מתודה to_input_list. מתודה זו מחזירה את כל ההודעות הישנות ואת ההודעה האחרונה שה AI השיב.

  3. באמצעות שמירת אוביקט התוצאה ושליחת ההודעות הישנות שוב ושוב ל Runner.run אנחנו מקבלים חוויה של שיחה המנוהלת בצד הלקוח.

מנגנון Sessions של ספריית הסוכנים מאפשר ניהול אוטומטי של העברת ההודעות הישנות. בדוגמה שראינו ההודעות נשמרות בבסיס נתונים SQLite שנשמר בזיכרון. בהמשך הסידרה נראה איך להשתמש במנגנון גם כדי לשמור את ההודעות בבסיס נתונים אמיתי וגם לערוך הודעות ישנות.

3. עכשיו אתם

אחד הדברים שהופכים סוכנים ל"ייחודיים" הוא הודעות המערכת, בדוגמאות הקוד שכתבנו זה מאפיין ה instructions שאנחנו מעבירים לסוכן:

agent = Agent(name="Assistant", instructions="Reply very concisely.")

עדכנו את התוכנית ושנו את מחרוזת ה instructions כדי לייצר סוכנים מסוגים שונים: סוכן שמלמד אנגלית, סוכן מכירות או יועץ לאורח חיים בריא.