Головна / Статті

Створення агента ReAct у LangChain: виконавці, Scratchpads та їхні обмеження

Створіть агента ReAct, який використовує інструменти, подивіться, як агент та AgentExecutor ділять роботу, і дізнайтеся, чому LangGraph краще справляється з контрольним потоком, циклами та станом.

Видавець: REACTAPP.TOP12 хв читання2719 слів

Джерела: Langchain Part 17 — End to End Agent Building

Що таке агент

Штучний інтелект-агент — це система, яка бере від людини загальну мету, а потім самостійно планує, приймає рішення та діє. Вона виконує послідовність кроків, використовуючи зовнішні інструменти, API чи джерела знань, зберігає контекст протягом усього процесу, міркує між кількома кроками, коригується при отриманні нової інформації та працює над досягненням бажаного результату.

У спрощеному вигляді агент — це LLM разом із деякими інструментами. LLM виконує міркування та прийняття рішень, а інструменти здійснюють дії.

Характеристики агента

  • Орієнтований на мету. Ви вказуєте, чого хочете, а не як цього досягти.
  • Самостійно планує. Агент розділяє проблему та впорядковує завдання без допомоги.
  • Використовує інструменти. Він викликає API, калькулятори, засоби пошуку та подібне. LLM знає, які інструменти існують та коли кожен з них потрібен.
  • Розуміє контекст. Він зберігає інформацію між кроками, тож попередні результати впливають на подальші дії.
  • Адаптивний. Коли щось змінюється — наприклад, API не працює або бракує даних — він коригує план.
  • Агент у коді

    Наведений нижче скрипт створює невеликий агент із двома інструментами: пошук у Інтернеті через DuckDuckGo та перевірка погоди, і ставить йому двокомпонентне запитання. Для отримання даних про погоду потрібен власний API-ключ від постачальника погодних даних; тут він показаний як замінник.

    from langchain_openai import ChatOpenAI
    from langchain_core.tools import tool
    import requests
    
    from langchain_community.tools import DuckDuckGoSearchRun
    
    from langchain.agents import create_react_agent, AgentExecutor
    from langchain import hub # It is a place from where we can get many type of prompts, so if we want any predefined prompt, we can get it from here
    
    # Step 1: Creating tool definitions
    search_tool = DuckDuckGoSearchRun()
    
    @tool
    def get_weather_data(city: str) -> str:
      """
      This function fetches the current weather data for a given city
      """
      url = f'https://api.weatherstack.com/current?access_key=4d1d8ae207a8c845a52df8a67bf3623e&query={city}'
      response = requests.get(url)
      return response.json()
    
    llm = ChatOpenAI()
    
    # Step 2: Pull the ReAct prompt from LangChain Hub
    prompt = hub.pull("hwchase17/react")  # pulls the standard ReAct agent prompt
    # The agent which we are gonna make is a ReAct agent (reasoning + action = ReAct)
    # ReAct is a design pattern
    
    # Step 3: Create the ReAct agent manually with the pulled prompt
    agent = create_react_agent(
        llm=llm,
        tools=[search_tool, get_weather_data],
        prompt=prompt
    )
    
    # Step 4: Wrap it with AgentExecutor
    agent_executor = AgentExecutor(
        agent=agent,
        tools=[search_tool, get_weather_data],
        verbose=True # whatever the agent thinks, it will be visible to us
    )
    
    # Step 5: Invoke
    response = agent_executor.invoke({"input": "Find the capital of Madhya Pradesh, then find it's current weather condition"})
    print(response)
    
    '''
    Entering new AgentExecutor chain...
    I should first find out the capital of Madhya Pradesh and then check the current weather condition for that city.
    Action: duckduckgo_search
    Action Input: "capital of Madhya Pradesh" Madhya Pradesh, state of India that is situated in the heart of the country. It has no coastline and no international frontier. Its physiography is characterized by low hills, extensive plateaus, and river valleys. The capital is Bhopal, in the west-central part of the state. Bhopal, city, capital of Madhya Pradesh state, central India. Situated in the fertile plain of the Malwa Plateau, the city lies just north of the Vindhya Range, along the slopes of a sandstone ridge. It is a major rail junction and has an airport. Pop. (2001) 1,437,354; (2011) 1,798,218. Bhopal was Indore (/ ɪ n ˈ d ɔːr / ⓘ; ISO: Indaura, Hindi: [ɪn̪d̪ɔːr]) is the largest and most populous city in the Indian state of Madhya Pradesh. [15] It is the commercial hub of Madhya Pradesh. It is consistently ranked as the cleanest city in India. [16] It serves as the headquarters of both the Indore District and the Indore Division.It is also considered the state education hub and ... In 1956, Bhopal became part of the state of Madhya Pradesh. Bhopal district was carved out on October 2, 1972, and is one of the 45 districts in the state. 4. Why is Bhopal famous? Bhopal is the capital city of the Indian state of Madhya Pradesh. It is known as the City of Lakes due to the presence of various natural and artificial lakes. In 1948, Madhya Bharat was created, with Indore designated as its summer capital and Gwalior as its winter capital. This arrangement highlights Indore's significance even then. However, Madhya Bharat was a temporary entity, and the map of central India was soon to be redrawn. The Creation of Madhya PradeshNow that I know the capital of Madhya Pradesh is Bhopal, I can use the get_weather_data function to check its current weather condition.
    Action: get_weather_data
    Action Input: Bhopal {'request': {'type': 'City', 'query': 'Bhopal, India', 'language': 'en', 'unit': 'm'}, 'location': {'name': 'Bhopal', 'country': 'India', 'region': 'Madhya Pradesh', 'lat': '23.267', 'lon': '77.400', 'timezone_id': 'Asia/Kolkata', 'localtime': '2025-05-01 17:52', 'localtime_epoch': 1746121920, 'utc_offset': '5.50'}, 'current': {'observation_time': '12:22 PM', 'temperature': 40, 'weather_code': 116, 'weather_icons': ['https://cdn.worldweatheronline.com/images/wsymbols01_png_64/wsymbol_0002_sunny_intervals.png'], 'weather_descriptions': ['Partly Cloudy '], 'astro': {'sunrise': '05:47 AM', 'sunset': '06:48 PM', 'moonrise': '08:38 AM', 'moonset': '11:01 PM', 'moon_phase': 'Waxing Crescent', 'moon_illumination': 15}, 'air_quality': {'co': '510.6', 'no2': '1.665', 'o3': '180', 'so2': '10.175', 'pm2_5': '29.045', 'pm10': '68.635', 'us-epa-index': '2', 'gb-defra-index': '2'}, 'wind_speed': 12, 'wind_degree': 302, 'wind_dir': 'WNW', 'pressure': 1005, 'precip': 0, 'humidity': 7, 'cloudcover': 25, 'feelslike': 40, 'uv_index': 1, 'visibility': 6, 'is_day': 'yes'}}The current weather condition in Bhopal, Madhya Pradesh is partly cloudy with a temperature of 40°C.
    Final Answer: The capital of Madhya Pradesh is Bhopal, and the current weather condition in Bhopal is partly cloudy with a temperature of 40°C.
    
    > Finished chain.
    {'input': "Find the capital of Madhya Pradesh, then find it's current weather condition", 'output': 'The capital of Madhya Pradesh is Bhopal, and the current weather condition in Bhopal is partly cloudy with a temperature of 40°C.'}
    '''
    
    response['output']
    # The capital of Madhya Pradesh is Bhopal, and the current weather condition in Bhopal is partly cloudy with a temperature of 40°C.
    

    П’ять пронумерованих кроків у скрипті охоплюють визначення інструментів, отримання стандартного запиту ReAct з хабу LangChain, створення агента, його обгортання в виконавець та його запуск. Трасування, надруковане в кінці, показує, що агент спочатку вирішує шукати столицю, а потім перевіряє погоду.

    ReAct

    LangChain підтримує кілька підходів до проектування агентів. Той, про який йдеться тут, — це ReAct, скорочення від Reasoning plus Acting. Він дозволяє моделі чергувати внутрішнє міркування, тобто процес формування думки, та зовнішні дії, такі як виклик інструментів, у структурованому циклі, який охоплює кілька кроків.

    Модель не формує свою відповідь одразу. Вона міркує крок за кроком, вирішує, що робити далі, і може використовувати такі інструменти, як API, калькулятори чи пошук в Інтернеті, для отримання допомоги.

    Ця схема підходить для:

    • задач, які вимагають кількох кроків;
    • завдань, що потребують використання інструментів;
    • ситуації, коли потрібно, щоб логіка була видимою та піддається перевірці.

    Як приклад, запитайте модель про населення столиці Франції. Спочатку вона робить висновок, що мусить визначити столицю, шукає інформацію, бачить, що відповідь — Париж, потім робить висновок, що їй потрібно населення Парижа, знову шукає та нарешті дає відповідь.

    ReAct складається з п’яти елементів:

    • Мислення. Приватна логіка агента, під час якої він оцінює поточний стан та планує наступний крок. Вона пояснює, чому обрано певний інструмент або що ще залишається невідомим.
    • Дія. Рішення використати один із інструментів з доступного набору, вказане через функцію чи API для виклику.
    • Вхідні дані для дії. Аргументи, які передаються цьому інструменту. Якщо дія — search, вхідними даними є сам текст запиту, наприклад, інформація про погоду в Делі.
  • Спостереження. Чисті дані, які інструмент повертає після виконання завдання. Агент читає їх, щоб визначити, чи завершено роботу, чи потрібні додаткові кроки.
  • Кінцева відповідь. Заключна відповідь, яка формується, коли агент вирішує, що інформації достатньо; вона об’єднує всі спостереження у зрозумілій мові.
  • Шаблон запиту, який керує цим циклом, виглядає так:

    Answer the following questions as best you can. You have access to the following tools:
    
    {tools}
    
    Use the following format:
    
    Question: the input question you must answer
    Thought: you should always think about what to do
    Action: the action to take, should be one of [{tool_names}]
    Action Input: the input to the action
    Observation: the result of the action …
    (this Thought/Action/Action Input/Observation can repeat N times)
    Thought: I now know the final answer
    Final Answer: the final answer to the original input question
    
    Begin!
    
    Question: {input}
    Thought:{agent_scratchpad} —
    

    У цій шаблоні спостереження — це просто те, що повертається після виконання інструментом своїх функцій.

    Робочий блок агента

    Робочий блок функціонує як короткострокова пам’ять або робочий зошит агента. Він фіксує історію поточного завдання: попередні думки, виконані дії, такі як виклики інструментів, та спостереження, які були отримані.

    Читаючи цей зошит, агент пам’ятає, що він вже з’ясував столицю Франції та тепер має знайти кількість населення Парижа. Це тимчасове зберігання, яке оновлюється щоразу, коли виконавець надсилає нову інформацію. Як тільки остаточна відповідь надсилається користувачеві, робочий блок зазвичай очищується або архівується, оскільки його завдання щодо цього завдання завершено.

    Назва має сенс, якщо згадати, що LLM є безстановим. Він не може природним чином пам’ятати те, що сталося кілька секунд тому у циклі коду. Тому LangChain бере всю історію поточного циклу та знову вставляє її у запит щоразу, коли запитує агента, що робити далі.

    Agent versus AgentExecutor

    Ці дві частини виконують окремі завдання.

    Агент — це мислитель, щось на кшталт менеджера проєктів. Він читає запит, розділяє його на менші кроки та вирішує, які інструменти потрібні. Його вхідні дані містять як запит користувача, так і все, що було зроблено досі.

    AgentExecutor — це виконавець, більше схожий на асистента. Він слухає інструкції агента, фактично запускає код для кожного інструменту та повертає результати.

    Інший спосіб поглянути на це: агент — це архітектор, який складає креслення, а виконавець — це бригада будівельників, яка зводить будівлю. Без агента немає плану, а без виконавця план ніколи не виходить за межі паперу.

    Виконавець координує весь цикл:

    1. Він надсилає вхідні дані та попередні повідомлення агенту, щоб той знав про запитання та про те, що вже сталося.
    2. Він отримує наступну дію від агента.
    3. Він запускає відповідний інструмент із наданими даними.
    4. Він додає результати роботи інструменту до історії.
    5. Він надсилає оновлену історію разом із запитанням користувача назад агенту, і цей процес повторюється, поки агент не вказує «Остаточна відповідь».

    Візьмімо запит на отримання температури в Делі та помножимо його на 10. Агент вирішує, що потрібен інструмент для отримання погодних даних, виконавець його викликає, надходять дані спостереження, агент вирішує, що потрібне множення, виконавець його виконує, і нарешті агент надає відповідь. Виконавець виконує все, що вирішує агент.

    Обмеження цього підходу

    Готовий виконавець підходить для простих випадків, але має серйозні слабкості, коли агенти стають більш складними. Нижче наведено порівняння з LangGraph — бібліотекою на основі графів від LangChain. Також зверніть увагу, що нові версії LangChain рекомендують використовувати LangGraph для агентів, тому перевіряйте актуальну документацію перед використанням старих класів виконавців.

    1. Чорна скринька

    Стандартний AgentExecutor вже попередньо налаштований. Достатньо надати йому інструменти та інструкції, і невидимий while-цикл продовжуватиме працювати, доки справа не буде завершена. Втрутитися в його роботу складно. Якщо ви хочете, щоб агент завжди запитував людину перед тим, як витрачати гроші, або дотримувався певної послідовності, наприклад спочатку крок А, потім крок B, екзекутор чинить опір, оскільки він розроблений для повної автономності.

    Уявіть собі агента з інструментами search_flights та book_flight. Усередині екзекутора LangChain ШІ вирішує, що робити далі, у прихованому циклі. Якщо його попросити забронювати рейс, він може негайно здійснити пошук та бронювання без запиту, можливо, за тариф у десять тисяч доларів, тоді як користувач хотів спочатку схвалити будь-яку покупку. Проміжні кроки, такі як обов’язкове схвалення, неможливо суворо застосувати, оскільки потік керування є неявним та контролюється моделлю.

    У LangGraph робочий процес визначається як послідовні кроки або вузли, такі як пошук рейсів, запит на схвалення та бронювання. Вони з’єднані так, що система повинна спочатку отримати схвалення, перш ніж здійснити бронювання. Це забезпечує повний контроль та полегшує застосування правил, додавання людських контрольних точок, повторних спроб чи умовних гілок.

    2. Цикли та ланцюги

    Справжні робочі процеси рідко є лінійними. Вони включають повернення назад, виправлення помилок та повторне оброблення наборів документів.

    • Ланцюги LangChain переважно розроблені як орієнтовані ациклічні графи, тож дані передаються лише в одному напрямку.
    • LangGraph створений для обробки циклів. Він моделює потік як карту, у якій вузли є функціями, а ребра — шляхами між ними.

    Для завдання з відповідями на запитання щодо документів пайплайн LangChain може отримати документи, написати відповідь та повернути її. Якщо відповідь є неправильною або неповною, він не може автоматично повернутися для повторної заготівлі даних чи уточнення запиту без додаткової ручної логіки. Як тільки процес рухається далі, йому важко повернутися назад для вдосконалення.

    LangGraph дозволяє явно створювати цикли: отримати дані, дати відповідь, перевірити якість, а якщо результат поганий — уточнити запит та знову отримати дані, повторюючи цей процес до отримання хорошого результату. Система може циклічно переходити між вузлами до досягнення певної умови, що підходить для завдань, які потребують ітерацій, корекцій та зворотного зв’язку.

    3. Стан та стабільність зберігання

    Це має найбільше значення для масштабованості.

    Пам’ять LangChain переважно стосується контексту розмови, наприклад, зберігання попередніх повідомлень у чаті, щоб модель могла давати кращі відповіді. Вона не тісно пов’язана з процесом виконання завдань та не відстежує прогрес у виконанні завдання. Якщо її не зберегти спеціально, вона зазвичай втрачається під час перезапуску системи, тому довготривалі завдання не є надійними.

    LangGraph розглядає пам’ять як повний стан процесу виконання завдань, а не лише історію чату. На кожному кроці він зберігає те, що було зроблено, які результати отримано та що буде далі. Якщо процес зупиняється на півдорозі, його можна продовжити саме з того місця, де він зупинився. Він також дозволяє призупиняти, перевіряти та редагувати стан за участю людини, або навіть повертатися до попереднього кроку, що робить складні багатокрокові завдання набагато надійнішими.

    Уявіть собі тривале завдання, наприклад обробку десяти документів по одному, яке зупиняється на 7-му кроці. Без вбудованої функції зберігання всі дані втрачаються, і доводиться починати з нуля, без жодних записів про прогрес за замовчуванням. Завдяки збереженню стану після кожного кроку можна продовжити роботу з 7-го кроку. Також можна зупинитися, дати комусь можливість переглянути чи внести зміни до стану, а потім продовжити, або повернутися до попереднього кроку — це своєрідна подорож у часі. Довгі робочі процеси стають надійнішими, дозволяють продовжувати роботу та їх легше дебагувати чи аудитувати.

    Головний висновок полягає у тому, що базовий виконувач ускладнює створення масштабованих агентів промислового рівня, саме тому існують інструменти на основі графів для виконання таких завдань.

    Пов’язана література

  • Самовідновлюваний Kubernetes на практиці: три збої, сигнали SigNoz та схвалені способи виправлення — розглянемо цикл збоїв, вимкнення через нестачу пам’яті та різкий зріст кількості токенів у кластері Kind, подивимося, що показує SigNoz для кожного випадку, та що потрібно посилити перед використанням AI-агента для усунення проблем.
  • Система RAG з LangChain з нуля: завантажувачі, фрагменти, ембеддинги, оцінка — поетапно створимо систему запитань та відповідей до документів: завантаження файлів, розділення на фрагменти, створення ембеддингів, етапи індексування та пошуку, а також способи оцінки якості отриманих відповідей.
  • Створення вашого першого агента LangChain за допомогою LangGraph у 2026 році — Поступово створіть агента LangChain за допомогою LangGraph, інструментів, функцій зберігання даних та відстеження, уникніть чотирьох поширених помилок та дізнайтеся, як це використовувало відділення підтримки одного буткемпу.
  • Чому розробка фронтенду складна після React: стан, ефекти, межі та інструменти ШІ — React ускладнив створення інтерфейсів, але не полегшив їхнє проектування. Справжньою роботою у фронтенд-розробці є визначення місця зберігання стану, усунення заплутаних ефектів, встановлення системних меж та робота з кодом, створеним ШІ.
  • Практичні нотатки: ваш AI-агент стикається з перешкодою на кроці 12. Deep Agents від LangChain — детальний посібник з Практичних нотаток: ваш AI-агент стикається з перешкодою на кроці 12. Deep Agents від LangChain: контракти, перевірки та готові фрагменти коду для команд, які використовують цю схему.