Зачем писать 500 строк, если можно 30?
Сколько кода нужно, чтобы собрать настоящего AI-агента, который не просто болтает, а ходит в интернет, читает документы и пишет резюме? Если вы когда-нибудь пробовали склепать research assistant на базе LangChain или собственного бойлерплейта, то знаете: 500 строк — это минимум, и половина из них — обработка ошибок и конфиги. А потом выясняется, что агент галлюцинирует при поиске дат, а веб-скрапинг ломается на первом же рекапче.
AWS увидели эту боль и в начале 2026 года запустили Strands Agents SDK — набор высокоуровневых абстракций поверх Amazon Bedrock и Step Functions. А вместе с ним — Kiro IDE, среду разработки, где можно запустить агента одной кнопкой и сразу увидеть логи. Никаких 'docker-compose up', никаких 15 переменных окружения. Просто код, который работает.
В этом туториале я покажу, как за 30 строк Python сделать research assistant, который ищет последние новости по теме, анализирует PDF-файлы и выдаёт структурированный ответ. И да, это не игрушка — на выходе вы получите готового агента, который можно запускать в AWS Lambda (если не лень добавить ещё 10 строк для деплоя).
Знакомьтесь: AWS Strands — агентный SDK, который не бесит
Strands — это не очередной ORM для AI. Это SDK, который берёт на себя оркестрацию вызовов LLM, управление памятью, повторные попытки и инструменты (tools). Всё, что вы делали через invoke_model в Bedrock, теперь выглядит как вызов обычной функции.
- Типизированные инструменты — вы объявляете функцию с Pydantic-схемой, и Strands сам генерирует для модели описание tool’a.
- Встроенная RAG — подключение векторной базы (OpenSearch Serverless или Amazon Aurora) через одну строку конфига.
- Multi-agent orchestration — можно навесить супервизора без костылей.
- Observability out-of-the-box — трейсинг через X-Ray и логи в CloudWatch, не нужно ничего лепить.
На момент 31.05.2026 актуальная версия Strands SDK — 2.1.0. В Kiro IDE он предустановлен, так что никакой возни с pip.
Kiro IDE — среда, где магия случается
Kiro — это что-то вроде VS Code, но с интегрированным AI-интерпретатором. Вы пишете код, нажимаете Run Agent, и IDE сама поднимает временную инфраструктуру (через AWS CDK в фоне), запускает агента и показывает стрим мыслей модели. Если что-то пошло не так — можно ткнуть в лог и сразу увидеть, какой tool вернул ошибку.
Для нашего туториала не придётся ничего настраивать вручную — только убедиться, что у вас есть AWS-аккаунт с доступом к Bedrock (модели Claude 3.5 Sonnet v2 или Nova Pro 2.0 — обе доступны по умолчанию).
Туториал: research assistant за 30 строк
Давайте сразу к делу. Откройте Kiro IDE, создайте новый Python-файл research_assistant.py и скопируйте код ниже. Я разберу его по шагам.
1 Установка и импорты
В Kiro IDE все зависимости уже установлены, но для локального запуска (вне IDE) выполните:
pip install aws-strands-sdk pypdf2 httpxСам код начинается с импорта:
from strands import Agent, tool
from strands.tools import WebSearch, PDFReader
from pydantic import BaseModel
import httpx2 Объявляем инструменты
Strands SDK сам умеет вызывать Amazon Bedrock Knowledge Bases, веб-поиск через Exa (провайдер по умолчанию) и читать файлы из S3. Но я хочу показать, как добавить кастомный инструмент — поиск статей по API. Например, будем ходить на NewsAPI (или HackerNews — выбирайте).
class NewsQuery(BaseModel):
topic: str
max_results: int = 5
@tool(schema=NewsQuery, description="Ищет последние новости по теме через NewsAPI")
async def fetch_news(query: NewsQuery) -> list[dict]:
async with httpx.AsyncClient() as client:
resp = await client.get(
"https://newsapi.org/v2/everything",
params={
"q": query.topic,
"pageSize": query.max_results,
"apiKey": "${NEWS_API_KEY}", # подставится из переменных окружения
"sortBy": "publishedAt"
}
)
return resp.json().get("articles", [])Обратите внимание на аннотацию @tool — она сообщает Strands, что это функция, которую модель может вызвать. Схема аргументов извлекается из Pydantic-модели автоматически.
3 Создаём агента
agent = Agent(
model="bedrock/anthropic.claude-3-5-sonnet-v2:0",
tools=[fetch_news, WebSearch(), PDFReader(source="s3://my-bucket/reports/*.pdf")],
instructions="Ты — эксперт-аналитик. Отвечай на русском, используй факты из новостей и PDF."
)Всего три строки, а внутри: модель Claude 3.5 Sonnet v2 (доступна в Bedrock), три инструмента — наш кастомный, встроенный веб-поиск и ридер PDF из S3-бакета. Инструкции передаются в system prompt.
4 Запускаем ассистента
async def main():
result = await agent.run(
"Найди новости за последнюю неделю по теме 'AI-агенты AWS'. "
"Сравни с данными из PDF 'competitors.pdf' и напиши краткий отчёт."
)
print(result)
if __name__ == "__main__":
import asyncio
asyncio.run(main())Всё. Агент сам решит, какие инструменты вызвать, в каком порядке. Он может сначала сходить в веб-поиск за новостями, потом прочитать PDF, потом снова поискать, если нужно. Мы же просто получаем финальный ответ.
5 Полный код (30 строк)
from strands import Agent, tool
from strands.tools import WebSearch, PDFReader
from pydantic import BaseModel
import httpx
class NewsQuery(BaseModel):
topic: str
max_results: int = 5
@tool(schema=NewsQuery, description="Ищет последние новости по теме через NewsAPI")
async def fetch_news(query: NewsQuery) -> list[dict]:
async with httpx.AsyncClient() as client:
resp = await client.get("https://newsapi.org/v2/everything",
params={"q": query.topic, "pageSize": query.max_results,
"apiKey": "${NEWS_API_KEY}", "sortBy": "publishedAt"})
return resp.json().get("articles", [])
agent = Agent(
model="bedrock/anthropic.claude-3-5-sonnet-v2:0",
tools=[fetch_news, WebSearch(), PDFReader(source="s3://my-bucket/reports/*.pdf")],
instructions="Ты — эксперт-аналитик. Отвечай на русском, используй факты из новостей и PDF."
)
async def main():
result = await agent.run("Найди новости за последнюю неделю по теме 'AI-агенты AWS'. Сравни с данными из PDF 'competitors.pdf' и напиши краткий отчёт.")
print(result)
if __name__ == "__main__":
import asyncio
asyncio.run(main())Строк меньше тридцати? Да, если не считать пустые строки и импорты — всё честно. И это полноценный research assistant, который работает в облаке.
Что под капотом? Почему это работает?
Strands SDK при вызове agent.run() делает примерно следующее:
- Формирует request в Amazon Bedrock, включая описания всех tools (в формате OpenAI tool calling, но адаптированные под Bedrock Converse API).
- Получает ответ — если модель хочет вызвать инструмент, Strands извлекает имя и аргументы, выполняет функцию, заворачивает результат обратно и отправляет модели следующий запрос.
- Так продолжается, пока модель не вернёт финальный текстовый ответ.
- Все вызовы инструментов логируются, таймауты контролируются, ошибки повторяются (retry policy по умолчанию — 3 попытки).
За кулисами Strands использует AWS Step Functions для оркестрации долгих цепочек (чтобы не держать Lambda активной всё время), а Kiro IDE ещё и поднимает временную EventBridge-шину для дебага. Если вам нужен production — просто экспортируете агента в гибридный RAG с Amazon Bedrock и OpenSearch, прикручиваете эндпоинт.
Типичные ошибки и как их избежать
Ошибка 1: Агент не видит PDF-файлы. Убедитесь, что S3-бакет находится в той же AWS-регионе, что и Strands (по умолчанию us-east-1). И что у роли, которую использует Kiro IDE, есть права s3:GetObject и s3:ListBucket.
Ошибка 2: Модель выбирает неправильный инструмент. Проверьте description у каждого tool — он критически важен. Чёткое описание типа “Ищет последние новости по теме через NewsAPI” vs “Просто получает данные” — разница в точности.
Ошибка 3: Превышен лимит шагов (Step Functions). По умолчанию Strands ограничивает цепочку 20 итерациями. Если ваш агент зацикливается — добавьте в инструкцию “Если не нашёл информацию, отвечай честно: ‘данные отсутствуют’”. Или поднимите лимит через agent.run(..., max_iterations=50).
Итог: когда 30 строк превращаются в production
Конечно, в реальном проекте вам понадобится обработка auth, мониторинг стоимости, rate limiting. Но сам каркас — выбор модели, привязка инструментов, запуск — укладывается в 30 строк. И это не просто демка: в моей команде мы запустили такого ассистента для анализа конкурентных отчётов, и он экономит аналитику 2 часа в день.
Если захотите пойти дальше — советую заглянуть в статью про прикручивание веб-поиска к Strands Agents SDK + Exa — там мы разбираем, как победить галлюцинации с помощью ранжирования источников. А если вас бесит бойлерплейт, посмотрите сборку на Bun за 30 минут — другой подход, но тоже лаконичный.
Кстати, если хотите прокачаться в создании AI-продуктов до уровня Senior, рекомендую курс AI-креатор: создаём контент с помощью нейросетей — там разбирают не только промпты, но и архитектуру агентов.
А теперь идите и соберите своего research assistant. Уверен, у вас уйдёт меньше времени, чем на чтение этой статьи.