TL;DR
  • Агент в контексте LLM — это не магия, а цикл, в котором модель по шагам вызывает инструменты (bash, git, тесты, web) и получает от них обратную связь.

  • Такой агент умеет ориентироваться в живой кодовой базе, запускать компилятор и тесты, читать логи и документацию, поэтому генерирует и правит код куда надёжнее, чем «голая» модель в чате.

  • На реальных примерах (аутентификация через GitHub App, SQL-таблицы с JSON) видно, что агенты способны закрывать значимую часть рутины, но всё ещё легко делают критические ошибки в безопасности, производительности и архитектуре — без разработчика это не выдерживает продакшн.

  • Чёткие локальные правила (например, стиль схем в SQL) агенты готовы соблюдать лучше многих людей, если эти правила явно зафиксированы в коде и комментариях.

  • Самый перспективный вектор — запуск агентов в изолированных контейнерах с параллельной работой, редактируемыми diff’ами и новым пониманием того, что такое IDE и код-ревью в «agent-first» мире.

Это вторая часть рассказа моего опыта того, как адаптировать свой опыт программирования в мире, где с компьютером можно общаться как с собеседником. Первая часть была о том, как встраивать LLM в уже существующие инструменты (по сути, в автодополнение) и как аккуратная работа с промптами может заменить традиционный веб-поиск. Теперь я хочу поговорить о более сложной, но и более полезной практике — о том, как писать программы с помощью агентов.

Что агент представляет собой 

Есть смысл начать с определения слова «агент» в контексте LLM. Из-за хайпа вокруг ИИ этим словом уже давно стали разбрасываться, задолго до того, как агенты стали реально полезной конструкцией. В результате приходится продираться сквозь маркетинговый туман и налёт псевдомистики, чтобы вытащить из этого термина хоть какую-то пользу.

Для человека с инженерным бэкграундом сейчас есть простое определение: агент — это 9 строк кода. То есть агент — это цикл for, внутри которого вызывается LLM. LLM может выполнять команды и видеть их вывод без участия человека в контуре.

Пользователь → LLM (промпт) → вызов инструмента (bash, patch и т.п.) → результат инструмента → ответ модели и конец шага.

И всё. Как и в случае с любыми простыми вещами, вполне естественно хочется сказать: «ну и что?» Это же просто цикл for. Но результат — поразительное усиление возможностей «голой» большой языковой модели.

Программирование у доски

Представьте, что вы стоите у доски и маркером пишете на C функцию, которая проверяет, является ли строка корректной UTF-8. (у меня один раз такое было на собеседовании). То, насколько хорошо вы справитесь, зависит от вашего опыта программирования и от умения как-то компенсировать тот факт, что у вас нет под рукой внешних ресурсов. Вам нужно помнить правила кодирования UTF-8. Не перепутать синтаксис C со всеми другими C-подобными языками, которыми вы пользовались за свою карьеру (сначала имя, потом тип или сначала тип, потом имя?). В обычной жизни вам помогает компилятор: он ругается, если вы ошиблись, вы можете открыть спецификацию UTF-8, а главное — вы можете написать программу, раскидать по ней несколько printf и посмотреть, где всё пошло не так.

Просить LLM без агента написать код — всё равно что просить вас писать код на доске. Это упражнение на то, чтобы вытаскивать из головы полузабытые знания, запускать парсер на чудовищно неэффективном «железе» и одновременно пытаться не нафантазировать себе несуществующий, но якобы полезный программный интерфейс. Тот факт, что LLM способны придумывать программы с нуля, сам по себе потрясающее техническое достижение, и я считаю большой удачей жить в эпоху, когда это стало возможным. Но не слишком удивительно, что простое подключение GPU к виртуальной белой доске не превращает её в по-настоящему полезный инструмент для разработки.

А что, если дать LLM больше, чем виртуальную доску? Что, если она сможет вызвать компилятор, увидеть ошибки компиляции и попробовать их исправить до того, как мы увидим результат? Что, если она сможет пользоваться grep и cat, чтобы читать существующие файлы в проекте? Что, если она сможет патчить сразу несколько файлов, включая модульные тесты, и многократно прогонять эти тесты? Агенты — это LLM, которые работают по обратной связи со средой.

Агенты — это LLM с обратной связью со средой

Так же, как люди лучше работают в среде с обратной связью, LLM переходят из разряда «классных демо» в разряд полезных программистов, если дать им удивительно небольшой базовый набор инструментов, очень хорошо знакомых разработчикам:

  • bash(cmd)

  • patch(hunks)

  • todo(tasks)

  • web_nav(url), web_eval(script), web_logs(), web_screenshot(), и т.д.

  • keyword_search(keywords)

  • codereview()

Агенты отлично ориентируются в кодовой базе с помощью инструмента bash: find, cat, grep -R — ровно так же, как это делали мы, кто работал ещё до появления IDE, и привык так ходить по проектам. Ещё на старте агенту явно говорят, что изменения нужно коммитить в git, и он делает это, вызывая через bash команды git add, git commit и т.д.

Результат, по сравнению с LLM, которая генерирует код без этих инструментов, заметно отличается. В частности:

  • Использование API сильно улучшается, потому что агент может искать документацию в вебе и curl-ом подтягивать её в своё окно контекста.

  • Обратная связь от компилятора снижает количество синтаксических ошибок и выдуманных («сгаллюцинированных») интерфейсов.

  • Компилятор в полноценной среде разработки также улучшает работу с зависимостями: помогает LLM понять особенности именно той версии библиотеки, которая используется в проекте. (Хотя это всё ещё одно из слабых мест LLM: они могут использовать документацию от более новой версии API или делать предположения, верные только для старых версий зависимостей. Мы планируем решать эту проблему в sketch.dev.)

  • Падения тестов помогают находить ошибки в сгенерированном коде и вдобавок положительно влияют на то, что LLM начинает чаще писать тесты для нового кода.

  • LLM могут работать с кодовыми базами, которые целиком не помещаются в окно контекста, потому что они выборочно читают только нужные части проекта.

  • Агенты могут «пощупать» конечный результат сами: запустить код, сделать скриншот страницы в браузере, отдать его модели и дальше крутить CSS до приемлемого итогового рендера. Когда всё идёт совсем плохо, они читают логи сервера, находят там panic или другую критичную ошибку, правят её и добавляют тест.

Обратная сторона агентов — время. Один пользовательский запрос в одно предложение, который раньше требовал ответа на 200 токенов, теперь может раздуваться до десятков тысяч промежуточных токенов на вызовы инструментов, веб-поиск и многократные прогоны тестов проекта. Это занимает несколько минут, а здоровое количество выпиваемого за день кофе всё-таки ограничено.

Сегодня всё это может казаться дорогим (мой последний заметный коммит, целиком сделанный агентом, обошёлся мне в 1,15 $ API-кредитов!), но эта стоимость быстро уйдёт по мере того, как будут улучшаться чипы, на которых работают модели. GPU куда менее ограничены в своём будущем развитии, чем CPU, которые гораздо сильнее упираются в физические пределы (инструкционно-уровневый параллелизм, ILP, который выжимает компилятор, тоже способен лишь на ограничённый прирост). Тот факт, что мы до сих пор называем чипы для LLM «графическими» чипами, показывает, что экономической машине под индустрией софта ещё предстоит всерьёз перестроиться, прежде чем она по-настоящему сфокусируется на производительности LLM на ватт.

В конечном счёте агенты тратят CPU- и GPU-циклы на промежуточную работу, чтобы людям не приходилось делать её самим. Каждый раз, когда мне удаётся механизировать часть своего труда, я успеваю сделать больше, поэтому агенты стали для меня огромным шагом вперёд. Из-за нехватки часов в сутках я в итоге пишу лишь небольшую долю тех программ, которые хотел бы написать, и с помощью агентов я продвигаюсь чуть дальше по этому списку хотелок. Хотелось бы, чтобы всем так повезло, как мне в прошлом году. Поэтому я абсолютно убеждён, что агенты стоят серьёзных инженерных вложений в устранение их текущих ограничений.

Относительно легко увидеть пример того, как агент выполняет полезную работу. Подключите его к своему проекту, выделите небольшой кусок задачи, опишите его текстом и посмотрите, что он сделает. Приведу два примера.

Пример: аутентификация GitHub App

Расскажу о примере, где я использовал агента, чтобы проделать существенную часть работы над проектом. Я реализовал первую версию аутентификации через GitHub App для хостинговой версии sketch.dev, используя sketch. Агент сделал всё за 3–4 итерации обратной связи, пока я кликал по элементам интерфейса и искал ошибки. Это поразительное достижение. Легко отмахнуться от склейки известных API как от «не настоящего» программирования, но в моей практической карьере почти всегда было так: на каждый час действительно интересной разработки приходилось 10 и более часов скучной рутины с API, библиотеками, глючными компиляторами, системами сборки и неуклюжими менеджерами пакетов, чтобы этот один интересный час вообще имел смысл. Инструмент, который позволяет за 30 минут просто написать несколько аккуратно сформулированных предложений, пока я иду пылесосить детскую, и при этом не терять рабочего темпа, — бесценен.

Но вот теперь начинается работа. Агент реализовал тот поток аутентификации GitHub App, который мне был нужен. Он даже удовлетворил жёсткому требованию, которое я ему задал: я попросил обойтись без хранения токена на пользователя и вместо этого использовать глобальные приватные учётные данные приложения, чтобы всё работало именно от них и схема базы данных оставалась простой. Он справился! Но по пути сгенерировал довольно плохой код.

Во-первых, там была огромная уязвимость безопасности. Код позволял любому пользователю, который авторизовал приложение, работать с любым репозиторием, к которому было выдано право приложению, даже если у самого пользователя доступа к этому репозиторию не было. Катастрофа. К счастью, всё было настолько плохо, что на этапе тестирования с командой мы бы быстро это заметили — как только наши приватные репозитории начали бы появляться в списках репозиториев друг у друга. (И проблема была настолько очевидной, что я заметил её ещё до этого.)

Краткого описания проблемы для sketch.dev хватило, чтобы он её исправил: агент реализовал проверку авторизации пользователей, и сделал это правильно. Ещё одно впечатляющее достижение: я написал одно предложение — и получил переделанный, рабочий коммит в отдельной ветке.

Следующей проблемой стала производительность. Хотя новый код и работал, он стал бы чудовищно медленным, как только появилось бы несколько пользователей. Он формировал список репозиториев, к которым у пользователя есть доступ, так:

for install := range allAppInstallations {  
	for r := range install.Repositories() {  
		if r.IsCollaborator(user) {  
			// add to available repositories  
		}  
	}  
}

Это означало, что каждый раз, когда я хотел показать пользователю список репозиториев, которые он авторизовал, мне нужно было для каждой организации GitHub, которая разрешила использовать Sketch, сделать API-вызов, чтобы получить список её репозиториев, а затем для каждого репозитория сделать ещё один API-вызов, чтобы проверить, есть ли у этого пользователя доступ к репозиторию. То есть количество API-вызовов росло вместе с числом пользователей продукта, а это никуда не годится.

В итоге оказалось, что корень проблемы — моё исходное наивное требование не хранить пользовательские токены GitHub. У GitHub просто нет эффективных API-вызовов на уровне авторизации приложения, которые позволяли бы выяснить, к чему имеет доступ конкретный пользователь. Единственный эффективный способ — спросить, к чему имеет доступ сам auth token, и использовать уже пользовательский auth token.

Когда я это понял, я сказал Sketch откатить моё исходное требование и поступить наоборот: хранить пользовательские токены и использовать их для всего. Агент быстро придумал эффективные схемы вызова API.

Чтобы рассказать эту историю, мне понадобилось больше слов, чем я суммарно набрал в Sketch, когда просил его сгенерировать нужный мне код аутентификации для GitHub, и написание этого текста потребовало больше усилий, чем код-ревью, в которых мы нашли все проблемы. Я специально на этом акцентирую внимание, потому что очень легко выдернуть отдельный эпизод, показать ограничения и ошибки инструментов и на основании этого объявить их «бесполезными» или «опасными». Мой опыт совершенно другой. Текущие инструменты явно не могут заменить меня как разработчика, но с их помощью я за один день закрыл скучную задачу, с которой в обычном режиме провозился бы неделю. И заодно успел пропылесосить детскую.

Пример: соглашения по SQL и JSON

Вот пример задачи, которую моему агенту приходится решать регулярно, и с которой у него были заметные проблемы, пока я не нашёл способ ему помочь (и, на мой взгляд, этот пример хорошо отражает типичное ограничение, с которым люди сталкиваются, когда впервые пробуют LLM).

В Tailscale я познакомился с необычным стилем использования SQL: каждая таблица — это JSON-объект. Конкретнее: у таблицы есть только одна «настоящая» колонка, а все остальные — вычисляемые на основе JSON. Типичная таблица выглядит так:

CREATE TABLE IF NOT EXISTS Cookie (  
  Cookie   TEXT    NOT NULL AS (Data->>'cookie')  STORED UNIQUE, -- PK
  UserID   INTEGER NOT NULL AS (Data->>'user_id') STORED REFERENCES User (UserID),  
  Created  INTEGER NOT NULL AS (unixepoch(Data->>'created')) STORED,  
  LastUsed INTEGER AS (unixepoch(Data->>'last_used')) CHECK (LastUsed>0),  
  Data     JSONB   NOT NULL  
);

У такого подхода есть масса плюсов и минусов. Он работает как «дешёвый суррогат ORM»: для каждой таблицы есть «очевидный» тип данных, соответствующий каждой записи. Добавлять новые поля в схему очень просто. Можно сделать ADD COLUMN, если хочется, но не обязательно. Ограничения на столбцы в SQL выступают хорошей динамической проверкой качества вашего JSON. Минус — сильно увеличивается объём данных в одной строке. Все INSERT и UPDATE приходится строить в терминах JSON. Наполовину вы оказываетесь в мире документных БД, но при этом всё ещё можете писать старые добрые JOIN’ы. И так далее.

Если отбросить плюсы и минусы, наш агент часто спотыкался об этот стиль. Когда он создавал новые таблицы и колонки, он иногда следовал паттерну «вычисляемых колонок», а иногда — нет. Как только мы впервые добавили таблицу, которая не следовала этому подходу «все колонки вычисляются из JSON», агент запутался ещё сильнее и, казалось, стал практически случайным образом выбирать между стилями.

В итоге поведение агента оказалось очень просто поправить. В начале файла со схемой SQL я добавил описание из трёх предложений. Ключевая фраза там примерно такая: «в каждой таблице есть одна конкретная колонка Data с JSON, все остальные колонки — вычисляемые из неё», плюс комментарий у таблиц-исключений, которые не следуют этому правилу, с пояснением, что это именно исключения из нормы. После этого поведение агента сильно улучшилось.

Это немного контр-интуитивно. В моём опыте подобные инструкции инженеры чаще всего игнорируют. То ли сродне «баннерной слепоте», то ли проблема в том, что комментарии сложно поддерживать актуальными, то ли в том, что большинство комментариев не заслуживает внимания. Вместо этого индустрия обычно решает такие вопросы через не самую приятную рутину: человек, который не знает локальных правил, пишет PR «как умеет», получает комментарии, и ему говорят переделывать. LLM, похоже, относятся к комментариям гораздо серьёзнее — и, будем надеяться, это к лучшему.

Модели кода как «актив» и «долг»

Один из аргументов против использования LLM как инструмента генерации кода состоит в том, что написание кода — это лишь небольшая часть общей стоимости владения кодовой базой. Основная часть затрат, говорится в этом аргументе, — это постоянная работа с уже существующим кодом. Есть кодовые базы, для которых это действительно так. В сильно используемых продуктах с растущим числом пользователей и всё новыми способами использования системы инженеры и правда тратят большую часть времени на навигацию по неявным и плохо понятным взаимозависимостям внутри существующего кода. Для человека, чья работа в этом и заключается, компьютер, с которым можно поговорить, чтобы он выдал рабочий результат на запрос «реализовать сортировку пузырьком на Фортране», выглядит чем-то между игрушкой и помехой. Иногда это пытаются описать через финансовые метафоры вроде «активов» и «долгов», но я опущу эти сравнения — они всё равно никогда толком не ложатся.

Однако вопрос, верно ли такое представление об инженерии в целом, даже если оно правильно для части проектов, остаётся открытым. Лишь немногие программы доживают до состояния, когда они и сильно нагружены, и живут очень долго. Почти у всего очень мало пользователей, короткий жизненный цикл или сразу оба фактора. Не стоит распространять опыт инженеров, которые сознательно выбирают работу по обслуживанию больших и старых продуктов, на всю индустрию.

К счастью, нам не нужно отвечать на вопрос о том, как выглядит вся картина программирования целиком, чтобы понять, полезны ли агенты, потому что агенты потенциально полезны даже при сопровождении уже существующих продуктов. Агент — это не только генерация кода. Это LLM с набором инструментов, которая читает код и меняет его, редактируя файлы.

Агенты с тем же успехом удаляют код, с каким его добавляют.

В итоге результатом всё равно становятся изменения. Да, это означает «больше работы», потому что человек, который управляет агентом, всё равно должен понимать, какие именно изменения вносятся. Да, агенту пока может не хватать понимания, чтобы уверенно менять большие продукты. Но изменение — это конечная цель инженера, который пользуется инструментом, и агенты уже демонстрируют способность аккуратно редактировать проекты как минимум среднего размера. Это делает их потенциально полезными инструментами практически в любой области разработки. Если агенты пока «недостаточно хороши» (а это ещё большой вопрос, и его точно стоит проверять на практике), то они всё равно движутся в правильном направлении и уже обладают всеми фундаментальными возможностями, чтобы до этого уровня дорасти.

Связанная, но более сложная тема — один из редко проговариваемых аргументов в пользу трудных в использовании инструментов разработки (например, языков программирования вроде C с минимумом удобств и запутанными системами сборки). Считается, что такие инструменты выступают «охранниками на входе» в проект и не дают разрастаться низкокачественной, посредственной разработке. У вас не будет раздувшихся зависимостей в проекте, если никто не может разобраться, как добавить новую зависимость. Если вы верите в подобную логику, то всё, что упрощает написание кода — статическая типизация, сборка мусора, менеджеры пакетов и агенты на базе LLM — только ухудшает ситуацию. Если ваша цель — замедлить изменения и по возможности их избегать, то агент вам не помощник.

Почему агенты появились именно сейчас?

В отличие от слегка загадочных идей вроде трансформерной архитектуры, на которой держатся LLM, механическая обратная связь внутри LLM кажется чем-то «очевидным». Это интуитивно ясно всем, кто думает о инструментах для разработчиков: я работаю над этим уже больше года, но наша первая версия sketch.dev в январе, несмотря на встроенный в LLM инструментарий Go, по меркам того, что у нас есть сейчас, с трудом тянет на статус агента. (Разница в полезности между той первой версией sketch и текущим open-source проектом sketch поразительна.) Польза обратной связи также очевидна всем, кто занимается ML: обучение с подкреплением уже 50 лет является одним из краеугольных принципов этой области.

Ответ в том, что критически важная часть работы по превращению агентов в полезный инструмент лежит в процессе обучения базовых моделей. LLM образца 2023 года не могли по-настоящему управлять агентами, LLM 2025 года уже оптимизированы под это. Модели должны надёжно вызывать предоставленные им инструменты и уметь эффективно ими пользоваться. Мы только сейчас начинаем видеть передовые модели, которые хорошо с этим справляются. И хотя наша цель — в итоге полностью перейти на открытые модели, сейчас по нашим оценкам на задачах вызова инструментов они заметно отстают от самых мощных проприетарных моделей. Мы уверены, что через полгода ситуация изменится, но пока что по-настоящему полезные повторяющиеся вызовы инструментов — это новая способность базовых моделей.

Что дальше

Нелегко рассуждать о том, что будет дальше, в настолько быстро меняющейся области, где большинство инженеров пока вообще не пользуются этими инструментами. Но тем, кто их создаёт, об этом думать всё равно нужно.

Сегодня агентов чаще всего запускают либо в IDE, либо в склонированном репозитории на локальной машине разработчика. Это простой способ начать: несложно поставить форк VS Code или консольный инструмент и запустить его. Но у такого подхода есть два серьёзных ограничения.

Первое крупное ограничение в том, что агентам нужно много встроенных предохранителей, чтобы они не начали творить что попало. На одной из моих машин припрятаны продакшен-учётные данные, с помощью которых я могу делать деплой. Когда агент запускает команды, не возьмёт ли он эти данные и не запустит ли мой скрипт деплоя для своих незакоммиченных изменений? Чтобы этого избежать, если агент работает прямо на вашей реальной машине, приходится постоянно просить разработчика присматривать за вызовами инструментов и давать агенту явные разрешения на выполнение команд. И даже тогда остаются риски. Я могу один раз нажать «yes to all» на запуске curl, а потом забыть, что разрабатываемый мной веб-сервер на localhost пока без аутентификации и умеет читать произвольные файлы с диска. Упс, мои продакшен-учётные данные снова утекли.

Второе крупное ограничение в том, что требование запускать агента именно в уникальной, вручную настроенной среде разработки конкретного разработчика фактически заставляет нас выполнять агентов последовательно. Как уже упоминалось, одна из серьёзных слабостей агентов в том, что им нужно несколько минут на один «ход», чтобы выдать хороший результат (и, вероятно, так и будет в обозримом будущем). Один из способов лучше использовать наше время — когда инженер параллельно «ведёт» сразу несколько агентов, но при таком способе развёртывания сделать это на практике довольно сложно.

Мы в sketch.dev сейчас пробуем решить обе эти проблемы с помощью контейнеров. По умолчанию Sketch поднимает небольшое окружение разработки в контейнере с копией исходного кода, а раннер умеет извлекать git-коммиты из этого контейнера. Это позволяет запускать сразу много экземпляров параллельно. (Другие агенты тоже идут в эту сторону, в целом сейчас «агентные» решения — бурно развивающаяся область.)

Чтобы показать, как такой параллелизм работает на практике, расскажу, что происходило, пока я занимался той самой GitHub-аутентификацией из предыдущего примера.

В какой-то момент я уже собирался пожаловаться в рабочем чате на то, какой ужасный у меня получился интерфейс формы. Вместо этого я открыл второй экземпляр Sketch, вставил туда скриншот формы и написал: «это уродливо, сделайте, пожалуйста, менее уродливо». Потом вернулся к размышлениям об аутентификации, а когда через полчаса вспомнил, что вообще-то что-то туда отправлял, открыл результат и решил: да, стало лучше. Я попросил агента сделать rebase, он сам разобрал конфликт слияния (одна из моих самых нелюбимых задач!), и я запушил обновление. Это всё ещё было далеко от качества настоящего дизайнера, но определённо лучше того ужасного неоформленного макета, который я на скорую руку собрал для тестов.

В прежней жизни я бы завёл на это задачу в трекере, то есть сначала сделал бы пометку в своём личном to-do.txt, что «надо завести задачу», потому что задачи видны другим разработчикам и требуют более связного и конструктивного описания, чем просто прикрепить скриншот и написать: «это уродливо, поправьте». Одна из замечательных вещей в работе с агентом в том, что даже если у вас осталось совсем немного ментальных сил, есть неплохой шанс за 30 секунд текста получить что-то реально полезное. Честно говоря, вероятность того, что я когда-нибудь превратил бы эту запись в to-do.txt в полноценную задачу, была очень низкой.

Главный вывод из наших экспериментов с UX агентов за последние полгода в том, что у нас наконец-то появился достойный сценарий для «контейнеров для разработки».

Во что превратится IDE?

Один из вопросов, над которым мы сейчас много думаем: во что в такой среде превращается IDE? Допустим, мы начинаем работу с разговора с агентом. Исполняющее окружение в контейнере может быть полностью развёрнуто из GitHub, изменения показываются как diff и отправляются в виде ветки (или пулл-реквеста). Это вообще похоже на реальный рабочий процесс?

На практике многие коммиты, которые генерирует Sketch (или любой другой агент, который мы пробовали), нуждаются в человеческой доработке. По нашему опыту, когда разработчики только начинают пользоваться агентом, почти каждый коммит требует ручного вмешательства, но с практикой в написании промптов объём таких вмешательств заметно падает. Иногда правки сводятся к тому, чтобы отредактировать комментарий или переименовать переменную. Иногда — гораздо серьёзнее. Как всё это увязать с миром, где всё крутится в контейнерах?

Пока что у нас есть несколько рабочих процессов, которые нам очень нравятся, и которые другие агентные системы ещё толком не исследовали. Один из них — сделать окно diff редактируемым. Вы можете печатать прямо в правой части diff-окна Sketch, и изменения попадут в коммит и будут запушены за вас. Для правок в одну строку это отлично работает.

Для такого класса доработок, где хочется прогнать sed, пройтись grep по изменениям или как-то по-особенному запустить тесты, у нас очень хорошо зашёл подход с выдачей пользователю ssh-доступа к контейнеру. Можно зайти в shell (у нас в интерфейсе есть небольшой веб-терминал), а ещё это легко обернуть в vscode:// URL, который можно открыть напрямую в традиционной IDE — и иногда это как раз то, что нужно.

Наконец, мы даём возможность писать комментарии в стиле код-ревью прямо поверх diff в sketch.dev и отправлять их агенту как обратную связь. Комментарии, привязанные к строкам diff, сильно сокращают объём текста, который приходится набирать (и этот способ очень знаком нам по многолетней практике обычных код-ревью).

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

Заключительные мысли

Процесс изучения и экспериментов с технологиями на базе больших языковых моделей стал для меня упражнением в скромности. В целом я люблю учиться новому, когда меняется само искусство программирования: осваивать переход к многопоточному программированию, переосмыслять дизайн систем после того, как SSD вытеснили HDD и резко снизили задержки доступа, жить в мире, где вдруг всё оказалось доступно в одной и той же сети. Подобные сдвиги в индустрии — настоящее удовольствие. (Не путать с бесполезной вознёй вокруг очередного JavaScript-фреймворка, нового сервиса облачного провайдера или свежей системы оркестрации кластеров.) Эти вызовы влияли на то, как работают мои программы: выбор алгоритмов, языков, библиотек и так далее.

Но LLM, а точнее агенты, влияют на сам процесс написания программ новым образом, чем немного сбивают с толку. Буквально каждое базовое допущение о том, как я работаю, приходится пересматривать — и это переосмысление проходит через весь накопленный опыт. Бывают дни, когда кажется, что было бы проще, если бы я вообще не знал ничего о программировании и начинал с нуля. И всё это продолжает меняться.

То, как всё устроено сейчас, сильно отличается от того, что было шесть месяцев назад, и я не думаю, что мы уже вышли на какой-то устойчивый уровень. Думаю, многие нормы командного взаимодействия тоже будут меняться. Например, тот наполовину сломанный процесс формальных код-ревью, который сегодня принят в индустрии, больше не решает те проблемы, с которыми и раньше справлялся кое-как. Его нужно переизобрести. «IDE», которая никогда не была настолько интегрированной, как про неё говорили, тоже нужно радикально переделать и переосмыслить. Похоже, индустрия уже осознаёт это, но ещё не стала смотреть на всё сквозь призму подхода agent-first. Работы впереди много, и я подозреваю, что ещё через полгода всё снова будет выглядеть совсем иначе.

Работы впереди много, и я подозреваю, что ещё через полгода всё снова будет выглядеть совсем иначе. Любопытство и скромность помогут нам пройти через эти изменения, но, пожалуй, стоит поменьше зависать на форумах, где люди бесконечно спорят об этих технологиях. Такой спор — как раз работа для агента.


Если вам интересно не только экспериментировать с моделями, но и доводить ML-решения до продакшна, посмотрите курс OTUS «Machine Learning. Professional». На курсе оттачивают работу с данными, NLP, временными рядами и рекомендательными системами — с прицелом на реальные продуктовые задачи и работу ML-инженеров. Пройдите вступительный тест, чтобы узнать, подойдет ли вам программа курса.

Для знакомства с форматом обучения и экспертами приходите на бесплатные демо-уроки:

  • 8 декабря. KNN — интерпретируемый метод для задачи классификации и регрессии. Записаться

  • 17 декабря. Оптимизируем построение модели через Pipeline. Записаться

Комментарии (0)