Vibe Coding — простыми словами

12 июля 2026

Модная тема Vibe Coding. Но рассказывают о ней слишком сложно, на мой взгляд. Что значит подготовить проект к AI? Как настроить tools/mcp/rules/skills? RAG? Агенты и чаты? В этой статье постараюсь простыми словами рассказать, что это такое. Репозиторий с примером — https://github.com/stswoon/projectForLessons/tree/master/2026/test-ai

Выбор AI

Простыми словами: Chat — это когда ты задаёшь вопрос и опционально прикладываешь файл или картинку, а модель выдаёт текстовый ответ и опционально файл или картинку.

Agent — это тот же чат, только у него есть доступ к ОС и репозиторию: в результате он сам меняет файлы на компьютере или данные на сервере, например через REST-запросы. Agents = LLM + Tools. Tools — это руки агента (читай ниже).

Есть разные системы: KiloCode, Codex, Claude, Grok, ChatGPT, Gemini, Cursor.

Ради простоты — покупаем Cursor и отмечаем галочкой «не отсылать данные для обучения».

Инит проекта

Пишем в чате:

Создай Hello World проект на React + Typescript

Всё, проект готов. См. коммит 12d0fb082a41b1d83ae73111f56be63fe779dabc.

Подготовка проекта

Составь agents.md для проекта

Теперь все агенты читают agents.md. Для каждого агента используются разные подходы, но agents.md более-менее стал стандартом. В этом файле описываем базовые правила, правила кода, где смотреть про архитектуру, правила работы с файлами. См. коммиты f186247c631f28afff34ab515ec1fa99b794026e и 356a580b2c53c1980e469d04df9645579157502a.

Rules

- Я: "какие бы rules ты добавил в проект"
- Agent: "..."
- Я: "сделай"

Готово: появились .cursor/rules/*.mdc, которые описывают, что нужно делать с каждым файлом по фильтру globs внутри файла, либо всегда, если alwaysApply: true. Всё можно было бы положить в agents.md, и всё бы работало, однако тогда файл стал бы большим и занимал бы много места в контексте. А так агент подключает только описание и затем, если правило подходит, уже загружает полный текст в контекст — по globs или по description.

См. коммит b07aa5827fee7c7d650a503eaa36ea74b4c046a3.

Безопасность

В rules и agents.md следует добавить ограничения типа:

  • нельзя читать .env
  • нельзя отправлять конфиденциальные данные, секреты и пароли
  • нельзя менять такие-то файлы

Это называется защитный промптинг.

Agent Modes

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

  • agent — стандартный режим: может планировать и менять файлы
  • plan — планирует, но файлы не меняет; можно использовать, чтобы убедиться, что он сделает то, что вы хотите, а потом переключиться в режим agent
  • ask — ответы на вопросы, что-то типа стандартного режима ChatGPT
  • multitask — позволяет запускать sub-агентов (читай ниже)

Context

Обычно контекст ограничен 200k токенов. Токен на русском языке — это примерно 2 буквы. Токен на английском — примерно 5 букв. Это связано с тем, что в LLM было больше обучающих данных на английском. Читай это как кодировки в древности: английский занимал 1 байт, а всё остальное — уже 2 байта.

Итак:

  • на английском вы экономите в 2.5 раза, т.е. в контекст поместится больше, либо сэкономите на лимите токенов в месячной подписке; но согласен — на русском, возможно, легче воспринимать информацию (мы же тут для Vibe)
  • если контекст загружен больше чем на 50% (100k токенов), то агент начнёт путаться и забывать середину — как у человека: хорошо помнятся начало и конец
  • поэтому рекомендуется разбить задачи на части, чтобы уместиться, либо суммаризировать и начать новый чат с этой суммаризацией
  • также на каждую новую задачу лучше начинать новый чат — так агент меньше «думает» из-за большого количества информации
  • Context = system prompt + agents.md + rules + mcp + tools + [user input + LLM output] * N, поэтому первый запрос съедает много токенов
  • системный промпт — просто текст, типа «ты senior react/angular/spring/java/go developer»

Prompt

Просто текст, где вы просите агента что-то сделать, а он магически угадывает — прям как человек.

Подробный prompt

One Shot prompt — объяснять стоит так же, как и человеку. Не просто «сделать приложение», а как можно подробнее, например так же, как пишется история:

Создай приложение-аналог https://www.ilovepdf.com/jpg_to_pdf.

Нужно уметь:
1) разбивать pdf на страницы и давать скачивать png/jpg
2) склеивать разные pdf
3) склеивать jpg/png в pdf
4) уменьшать размер/качество jpg/png для последующего склеивания в pdf или скачивания
5) drag&drop страниц с изменением порядка
6) если pdf-страница является «текстом», а не картинкой, то она таковой и должна остаться, чтобы не увеличивать размер
(если это невозможно — сообщи об этом, и можно преобразовать в картинку)

Чем подробнее сделаете ТЗ, тем лучше он ответит. Хотя сейчас сети прокачались, поэтому часть информации для простых вещей он додумывает сам и понимает.

Также можно добавить json/open-api схемы, примеры запросов/ответов, арх. диаграмму — назовём это prompt + examples.

Итеративный prompt

Даёшь маленькую задачку, потом раскручиваешь. Например, в каждом новом чате:

  • создай react-приложение
  • добавь ts
  • добавь shadcn как ui-kit
  • падает ошибка такая-то, поправь
  • добавь тесты
  • добавь документацию

Например, см. коммиты add tailwind:

  • 1e6bc8e63033ae2a160b6da299ce1a397bfb0522 — «добавь tailwind»
  • e96e1b7355945aa00423ee8cb7c621a34332900e — «добавь shadcn» (он базируется на tailwind)
  • 9b04a338bbf80d8d019a3085b89ff2cbd7519c57 — «поправь ошибку сборки»

Skills

Чтобы каждый раз не писать промпт, чтобы добавить новый ui-компонент или опять провести ревью коммита, можно скопировать промпты в текстовый редактор и потом вставлять их из заметок, а можно создать папку .cursor/skills и потом просто написать /add-react-feature.

- Я: "какие skills ты бы добавил"
- LLM: "..."
- Я: "добавь: 1) commit-messages 2) add-react-feature 3) scope-guard 4) component-from-mockup"

См. коммит fc49042d39b97af6698049bd8f742fc7e4bfc94e.

Tools

Tools — это руки агента. Базовые возможности:

  • Terminal — выполнение команд в shell: npm, git, сборка, grep и т.д.
  • Read / Write / Grep — чтение, редактирование и поиск по файлам репозитория
  • Web Search — поиск в интернете
  • Browser — проверка запуска приложения
  • и др.

Без Terminal агент не был бы агентом, т.к. ничего бы не смог сделать. В принципе, на этом всё: всегда можно через терминал создать программу, которая вызовет то или иное API. Однако создание такой программы займёт полконтекста. Поэтому можно помочь агенту и создать удобный tool для него.

Создание своего Tool

Создай Tool для получения random-names из randomuser.me

См. коммит 5e53e3b31c8c3f240371ad53169e2b58914ddf70. Получаем 3 файла в папке .cursor/tools/random-names:

  • tool.md — описание по принципу One Shot prompt: название + что делает + когда вызывать + что вызывать (index.mjs)
  • schema.json — схема параметров
  • index.mjs — обычный node.js-код с вызовом API randomuser.me

Теперь, если спросить «дай мне случайные имена», система выдаст имена; при этом в thinking можно увидеть, что запускается именно наш tool, и увидеть raw-ответ tool'а. Raw-ответ также можно посмотреть в настройках Cursor в секции Tools — удобно для дебага.

Tool tags

Для систем вида n8n, где к агенту подключаются tools через drag-n-drop, а в системном промпте добавляется описание того, какие tools есть, и он соответственно вызывает либо запрос на сервер A или сервер B, либо отправку данных в Telegram или почту.

Видеодокументация про n8n:

MCP

По сути MCP тотже тул, только стандартизованный: их легко подключить в маркете Cursor или через глобальный mcp.json. Я подключил:

  • context7 — добавляет информацию про новые версии библиотек, которой нет у LLM, т.к. она обучалась несколько месяцев назад
  • playwright — для запуска тестов и работы с браузером: кликать на кнопки для проверки
  • chrome-devtools — дебаг ошибок
  • интеграции с системами — помогают легче доставать данные, ревьюить MR'ы, смотреть логи и др.
  • memory — смотри ниже

Memory MCP

Когда задаёшь вопрос ChatGPT, он может найти в истории релевантные диалоги и воспользоваться данными из них — так что создаётся впечатление, что чат адаптируется под тебя. Cursor и другие не умеют этого делать. Однако для этого есть Memory MCP.

Сходу я нашёл:

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

Довольно быстро установил @modelcontextprotocol/server-memory.

А вот с mempalace не смог разобраться.

С basic-memory были проблемы, но удобно, что можно видеть результат в md. Поэтому см. коммит 4386203927a80b61309675ac74878a2cf374e0ee.

1) `powershell -c "irm https://astral.sh/uv/install.ps1 | iex"` — ставим uv
2) `uv tool install basic-memory` — устанавливаем basic-memory
3) `mkdir D:\AI-memory`
4) add mcpServers
"basic-memory": {
  "command": "%USERPROFILE%\\.local\\bin\\uvx.exe",
  "args": [
    "basic-memory",
    "mcp"
  ]
}
5) добавить rule автосохранения — memory.mdc
6) добавить hook автосохранения после окончания сессии

Создание своего MCP

Создай local mcp для получения случайных цветов

См. коммиты e4aaaa6d926a61791aeb01fd725566a99a9656ad и 9ab9a1b851f20a1e7c60fd6d731279cc23630407.

Создаётся lib.mjs с основной логикой. Далее создаётся server.js и package.json, где по аналогии с tool.md регистрируем tool с его описанием.

import {McpServer} from '@modelcontextprotocol/sdk/server/mcp.js'
import {StdioServerTransport} from '@modelcontextprotocol/sdk/server/stdio.js'
import {z} from 'zod'
import {generateRandomColors} from './lib.mjs'

const server = new McpServer({name: 'random-colors-mcp', version: '1.0.0'})
server.registerTool(
    'random-colors-mcp',
    {
        title: 'Random Colors MCP',
        description: 'Генерирует случайные цвета в формате HEX (#RRGGBB)',
        inputSchema: {
            count: z.number().int().min(1).max(100).default(5)
                .describe('Количество цветов. По умолчанию 5, максимум 100.'),
        },
    },
    async ({count}) => {
        const colors = generateRandomColors(count ?? 5)
        return {
            content: [{type: 'text', text: colors.join('\n')}]
        }
    }
);

async function main() {
    const transport = new StdioServerTransport();
    await server.connect(transport);
}

Далее создадим .cursor/mcp.json, чтобы не применять глобально ко всем проектам, а только локально в нашем тестовом проекте:

{
  "mcpServers": {
    "random-colors-mcp": {
      "command": "node",
      "args": [".cursor/tools/random-colors-mcp/server.mjs"]
    }
  }
}

Самодельный RAG

RAG нужен, чтобы дать агенту новую информацию. Самый простой способ — закинуть все документы в контекст. Но тогда они не поместятся при больших объёмах. Поэтому можно создать векторную БД, которая по типу Elastic Search будет искать подходящую информацию — и если найдётся, то уже тогда документ, точнее чанк документа, подгружается в контекст.

Предположим, нам нужно сделать MCP для работы с нашим фреймворком.

  1. сгенерируй документацию по фреймворку, каждый компонент описывается отдельным субагентом, потом собирается в /docs

  2. добавим MCP с использованием библиотеки mcp-local-rag, которая генерирует RAG по папке:

{
  "mcpServers": {
    "local-rag": {
      "command": "npx",
      "args": ["-y", "mcp-local-rag"],
      "env": {
        "BASE_DIR": "D:\\mycode\\frontend-repo"
      }
    }
  }
}
  1. Зададим агенту вопросы, чтобы убедиться, что система правильно отвечает.

Multitask

Создай описание для мультиагентов для работы по диаграмме
                    ┌─────────────────┐
                    │  Lead / Planner │
                    │  декомпозиция   │
                    └────────┬────────┘
                             │
          ┌──────────────────┼──────────────────┐
          │                  │                  │
          ▼                  ▼                  ▼
   Architecture agent   UI/API agent       Test agent
   читает код,          изучает контракт,  ищет сценарии,
   предлагает план      UI kit, edge cases пишет тест-план
          │                  │                  │
          └──────────────────┴──────────────────┘
                             │
                             ▼
                   Implementation agent
                  пишет код в своём worktree
                             │
                             ▼
                     Review / QA agent
                проверяет diff, тесты, регрессии

Главный принцип — один агент владеет изменением конкретного файла или модуля. Два агента не должны одновременно редактировать CheckoutPage.tsx, общий Zustand store, package.json. Иначе получите конфликтующие diff'ы.

Получим skill /complex-task-orchestration и .cursor/agents/*.md. См. коммит 30cf77e460246040849e7411fe13436334c88eaa.

Теперь, если перейти в режим Multitask и запустить skill /complex-task-orchestration, то сначала Lead раздаст задачи, а потом 3 сабагента параллельно будут делать свои задачи — это позволит ускорить работу или улучшить результат за счёт цикла «написал developer — проверил QA — отправил на переделку».

Commit

Часто агент может сделать что-то не то. Поэтому после каждого ответа агента делайте коммит. Может случиться так, что первый и второй раз всё хорошо, а на третий раз код сломается — и захочется откатиться. Если между шагами не было коммитов, разобраться, какие из десятка изменённых файлов откатить, сложно. Проще всего вернуться к последнему коммиту; остальные способы распутывания изменений обычно сложнее. Поэтому всегда делайте коммит!

PDF-concatenator

Например, таким образом я создал приложение PDF-concatenator, которое на клиенте работает с PDF — тем самым ваши данные остаются защищёнными, т.к. никуда не отправляются.

Единственное — я заменил мультиагентов чуть на другую схему. Все чаты написаны (а их всего 6, по 2 промпта в каждом) в README.md.

Вот что получилось — https://pdf-concatenator.stswoon.ru