ИИ-коуч продаж на LiveKit – tool-calling и анализ экрана

Автор: Николай СапуновОбновлено: август 202623 мин чтения
Содержание статьи +

Коротко

Коуч продаж – это программный участник, который подключается к живому звонку с клиентом, слушает обе стороны, видит экран менеджера и подсказывает ему лично – но никогда клиенту. В этом уроке мы создаём такого коуча на базе LiveKit, добавляя три способности к «молчаливому ноутейкеру» из предыдущего урока: вызов инструментов (tool-calling), чтобы агент мог в ходе звонка быстро получить баттлкарту или карточку клиента из CRM; анализ экрана, чтобы видеть презентацию или демо; и приватный канал связи, чтобы советы доходили только до менеджера. Главное правило, обеспечивающее безопасность: коуч не взаимодействует ни с кем в комнате – он отправляет текстовые сообщения по адресному вызову (RPC) исключительно одному участнику – менеджеру, и клиент не слышит и не видит ни слова. К концу урока вы поймёте архитектуру, бюджет задержки, структуру издержек и правила согласия достаточно хорошо, чтобы внедрить эту функцию в продукт для видеосвязи или продаж.

Зачем это нужно

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

От ноутейкера к коучу: что меняется

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

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

Вот эти три дополнения – простыми словами, прежде чем мы перейдём к подробному разбору каждого.

Первое – tool-calling (вызов инструментов). Ноутейкеру никогда ничего не нужно было искать. Коучу – нужно: когда клиент говорит «мы уже используем Acme», коуч должен уметь найти баттлкарту по Acme; когда клиент называет свою компанию, коуч должен уметь подтянуть карточку этого аккаунта из вашей базы. Tool-calling – это механизм, позволяющий языковой модели сама решить, что ей нужно получить конкретную информацию, прежде чем ответить.

Второе – анализ экрана. Звонки по продажам – это не только разговор. Менеджер показывает экран: слайды, живое демо продукта, страницу с ценами – и коуч, не видя экрана, остаётся наполовину слеп. Мы даём коучу «глаза», подключаясь к видеопотоку демонстрации экрана и выделяя отдельные кадры, чтобы модель могла заметить: «менеджер всё ещё на вводном слайде на восьмой минуте» или «в демо только что возникла ошибка».

Третье и самое важное – приватный канал. Молчание ноутейкера было удобным; молчание коуча по отношению к клиенту – жёсткое требование. Коуч должен общаться только с менеджером и никому больше. Мы используем прямое адресное сообщение, которое сервер LiveKit доставляет исключительно одному участнику, так что подсказка остаётся структурно невидимой для всех остальных в комнате.

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

Непреложное правило: коуч приватен

Коуч продаж, которого слышит клиент, – это не инструмент коучинга, а инструмент саботажа. Вся система держится на одной гарантии: вывод коуча получает только менеджер, и больше никто. Ошибитесь здесь хоть раз в сделке – и вы раскрыли собственный плейбук (лимиты скидок, тезисы против конкурентов, вашу оценку покупателя) самому клиенту на записанном звонке. Поэтому приватность мы закладываем на уровне транспорта, а не надеемся, что промпт заставит модель промолчать.

LiveKit предоставляет ровно тот примитив, который нужен: удалённый вызов процедуры, или RPC – способ, с помощью которого один участник может вызвать именованную функцию у другого конкретного участника и получить ответ. Ключевое здесь слово – «конкретного». Когда агент вызывает perform_rpc, он обязан указать destination_identity. Сервер LiveKit доставляет это сообщение только одному участнику. Ни один другой участник комнаты его не получает. Клиент покупателя никогда не является адресатом, поэтому перехватывать нечего.

Рис. 1. Единственное правило, которое делает коуча безопасным: совет идёт по каналу, адресованному identity менеджера, никогда – как аудио в комнату и не как широковещание.

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

# В агенте: доставить подсказку ТОЛЬКО менеджеру.
await ctx.room.local_participant.perform_rpc(
    destination_identity=rep_identity,        # менеджер — никогда не клиент
    method="coach_nudge",                     # метод, который зарегистрировало приложение менеджера
    payload=json.dumps({
        "kind": "objection",
        "headline": "Возражение по цене — заякорить на ROI",
        "detail": "Сказали про бюджет. Откройте слайд ROI; назовите окупаемость за 6 недель.",
    }),
    response_timeout=4,                        # сдавайтесь быстро: запоздавшая подсказка — это шум
)

Три вещи в этом вызове отвечают за безопасность. destination_identity – это менеджер, установленный при подключении и переданный агенту; способ передачи описан в разделе про RAG. payload – обычный текст, ограниченный LiveKit до 15 KiB, что более чем достаточно для подсказки; мы отправляем небольшой JSON, чтобы UI менеджера мог по-разному отображать подсказку на возражение и подсказку со следующим вопросом. А response_timeout сделан коротким намеренно: коучинг – скоропортящийся продукт, поэтому если клиент менеджера не успевает подтвердить подсказку за пару секунд, мы её отбрасываем, а не позволяем прийти с опозданием и в неподходящий момент.

Парная половина размещается в клиенте менеджера и регистрируется один раз до вызова, чтобы быть готовой к моменту срабатывания агента:

# В приложении менеджера: принимать подсказки и рисовать их в приватной боковой панели.
@room.local_participant.register_rpc_method("coach_nudge")
async def on_coach_nudge(data: RpcInvocationData):
    tip = json.loads(data.payload)
    render_in_coach_panel(tip)   # панель, которую видит только менеджер
    return "shown"               # подтверждение обратно агенту

Поскольку RPC – это механизм «запрос–ответ», агент может определить, доставлена ли подсказка. Клиент менеджера возвращает краткое подтверждение; если же агент получает ошибку «адресат отключился» или «таймаут ответа», он понимает, что подсказка не дошла, и может не отправлять следующую, которая предполагает, что первую увидели. Один важный нюанс из спецификации, который стоит запомнить: участник, помеченный как «скрытый» (hidden), вообще не может выполнять RPC-вызовы, поэтому сам агент должен быть обычным, нескрытым участником – при этом он по-прежнему не публикует ни аудио, ни видео.

Резонный вопрос: почему не использовать широковещательное data-сообщение, которое LiveKit тоже поддерживает? Потому что широковещание по определению доставляется каждому участнику, и единственное, что отделяет его от экрана клиента, – это клиентский код, который сам решает проигнорировать сообщение. Это гарантия приватности, основанная на надежде. Адресный RPC переносит эту гарантию на уровень маршрутизации сервера, где ей и место. Правило на вынос: коуч не публикует аудиотрек и не рассылает данные по всей комнате – он общается только адресными сообщениями с одним получателем.

Способность первая: вызов инструментов

Когда канал безопасен, коуча можно сделать полезным. Первое новое чувство – это умение что-то искать, и в LiveKit Agents оно реализуется через вызов инструментов (tool calling).

Инструмент (tool) – это просто функция в коде вашего агента, которую вы разрешаете вызывать языковой модели. Вы пишете обычную Python-функцию, декорируете её, чтобы фреймворк её зарегистрировал, и составляете понятный docstring с описанием её назначения – модель читает этот текст и сама решает, когда следует вызвать функцию. Решение принимает модель; ваша задача – подготовить набор доступных действий и чётко описать каждое из них.

Для коуча продаж меню – это ваш процесс продаж, представленный в виде функций. Несколько таких функций нужны почти любому коучу:

from livekit.agents import function_tool, RunContext

@function_tool()
async def get_battlecard(self, context: RunContext, competitor: str) -> str:
    """Достать одностраничную баттлкарту по названному конкуренту, которого упомянул клиент.
    Используй в момент, когда всплывает конкурирующий продукт, чтобы менеджер мог его парировать."""
    return await battlecards.lookup(competitor)

@function_tool()
async def get_account_context(self, context: RunContext, company: str) -> str:
    """Подтянуть карточку CRM по компании клиента: открытые сделки, прошлые заметки,
    дату продления контракта. Используй рано, чтобы привязать совет к истории этого аккаунта."""
    return await crm.fetch(company)

@function_tool()
async def check_discount_authority(self, context: RunContext, percent: float) -> str:
    """Вернуть, вправе ли менеджер дать запрошенную скидку, и шаг согласования, если нет.
    Используй всякий раз, когда обсуждают цену или скидку."""
    return await pricing_rules.evaluate(self._rep_id, percent)

Читайте docstrings, а не только код. Каждый из них сообщает модели две вещи: что функция возвращает и когда её использовать. Фраза «используй в момент, когда всплывает конкурирующий продукт» – это не комментарий для людей, а реальная инструкция, которой модель действительно следует. Расплывчатые docstrings создают коуча, который вызывает не тот инструмент не в то время; точные – коуча, который ведёт себя как дисциплинированный пресейл-инженер.

LiveKit поддерживает два типа инструментов, и коуч по продажам использует оба. Функции, описанные выше, – это функциональные инструменты (function tools): код, который вы написали, работает на вашем сервере и взаимодействует с вашими системами. Второй тип – инструменты от провайдера (provider tools): возможности, которые запускаются на серверах вендора модели и подключаются к агенту одной строкой. Несколько ведущих вендоров предлагают такие провайдерские инструменты, как встроенный веб-поиск, поиск по загруженным файлам и выполнение кода. Для коуча провайдерский file-search – быстрый способ дать модели запрашивать ваши материалы по продажам, не создавая систему поиска с нуля в первый день, – хотя, как мы увидим в разделе про RAG, обычно от него в итоге отказываются.

Рис. 2. Один виток цикла коуча. Модель решает, нужно ли что-то искать, запускает инструмент к вашим системам, затем доставляет приватную подсказку – никогда не озвученный ответ.

Есть одна ловушка, уникальная для коуча в реальном времени – она касается не точности, а времени. Обычный голосовой ассистент может сделать паузу и сказать: «Секунду, проверю», пока работает медленный инструмент, потому что человек ждёт ответа. У коуча такой возможности нет: клиент продолжает говорить, независимо от того, успела ли CRM ответить. Если коуч блокирует весь цикл, ожидая трёхсекундный запрос к CRM, он отстаёт от разговора, а подсказка по теме, которой уже тридцать секунд, хуже, чем никакой.

Ответ LiveKit – асинхронные, или фоновые, инструменты: долгий запрос выполняется параллельно, не блокируя агента, так что модель продолжает обрабатывать новые реплики и возвращает результат, как только он готов.

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

Сделаем задержку конкретной, потому что именно это число определяет, будет ли фича казаться волшебной или сломанной. Допустим, клиент заканчивает предложение, а ваш конвейер выполняет: финализацию распознавания речи, принятие решения моделью о вызове инструмента, обращение к CRM и формирование подсказки.

финализация STT             ≈ 300 мс
модель решает + шлёт вызов    ≈ 400 мс
поход в CRM                   ≈ 500 мс
модель составляет подсказку   ≈ 500 мс
доставка RPC менеджеру        ≈ 50 мс
-----------------------------------------
итого                         ≈ 1 750 мс

Меньше двух секунд – от конца фразы клиента до подсказки на экране менеджера. Этого достаточно, чтобы быть полезным, но недостаточно быстро, чтобы казаться мгновенным: менеджер успевает прочитать подсказку в паузе между мыслями, а не сразу после последнего слова клиента. Урок про бюджет задержки до 100 мс объясняет, почему этапы обработки речи и сети занимают именно столько времени. Практический вывод здесь в том, что переход к инструменту – самый большой управляемый участок задержки, поэтому медленные инструменты стоит держать в фоне, а закэшированную или предварительно загруженную баттлкарту использовать вместо живого запроса к базе, если это возможно.

Способность вторая: анализ экрана

Второе чувство – зрение, а точнее, зрение разделяемого экрана менеджера. В LiveKit разделяемый экран публикуется как видеотрек – точно так же, как и камера: та же механика, но другой источник. Поэтому дать коучу «глаза» – значит подписаться на этот трек и преобразовать его видеопоток в отдельные кадры, которые модель сможет обработать.

Языковые модели не воспринимают видео так, как мы. Большинство из них обрабатывают кадр – одно неподвижное изображение – по отдельности. Поэтому коуч не передаёт в модель весь видеопоток; он делает выборку. Он берёт кадры по расписанию или в моменты, когда происходит что-то значимое, передаёт одно изображение модели вместе с актуальной транскрипцией и позволяет модели анализировать оба источника информации одновременно. Встроенная поддержка зрения в LiveKit берёт примерно один кадр в секунду, пока пользователь говорит, и один кадр каждые три секунды, когда он молчит, масштабируя каждый кадр так, чтобы он помещался в размер 1024 на 1024 пикселя, перед кодированием в JPEG. Эти параметры по умолчанию – разумная отправная точка; для разделяемого экрана их часто приходится снижать ещё сильнее, поскольку слайды меняются гораздо реже, чем выражение лица.

Рис. 3. Превращаем разделяемый экран в то, что модель может прочитать: выбрать трек демонстрации экрана, взять один кадр по расписанию, масштабировать и закодировать, прикрепить к следующей реплике.

Деталь, которая отличает работающего коуча от сбивающего с толку, – это какой трек вы семплируете. На звонке по продажам одновременно могут присутствовать несколько видеотреков: камера менеджера, камера клиента и разделяемый экран менеджера. Автоматический режим живого видео в LiveKit использует только один – самый недавно опубликованный видеотрек. Это удобно для ассистента с одной камерой, но не подходит для коуча: если клиент включит камеру после того, как менеджер начал демонстрировать экран, коуч вдруг начнёт видеть лицо клиента вместо презентации. Поэтому коуч не должен полагаться на автоматический режим. Вместо этого он перебирает опубликованные треки менеджера, выбирает тот, чей источник – демонстрация экрана, и семплирует именно его. У демонстрации экрана есть собственный источник трека – именно для того, чтобы отличать её от камеры; используйте это различие, а не угадывайте по времени публикации.

Вот выбор и семплирование, сведённые к сути:

from livekit import rtc

def attach_to_screenshare(self, rep: rtc.RemoteParticipant) -> None:
    # Выбираем именно трек ДЕМОНСТРАЦИИ ЭКРАНА, не камеру и не «самый недавний».
    for pub in rep.track_publications.values():
        if pub.source == rtc.TrackSource.SOURCE_SCREENSHARE and pub.track:
            self._frames = rtc.VideoStream(pub.track)
            break

async def latest_screen_frame(self):
    # Держим только самый свежий кадр; мы семплируем, а не стримим каждый кадр.
    async for event in self._frames:
        self._latest = event.frame

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

Две оговорки. Первая – стоимость, и она немалая. Каждый кадр, который вы семплируете, – это изображение, которое модель должна обработать, а вход для vision-обработки оплачивается за каждое изображение. Если семплировать 30-минутный звонок раз в три секунды – получится около шести сотен изображений; раз в секунду – уже около тысячи восьмидесяти. Поэтому частота семплирования – это прямой и линейный рычаг издержек: самый дешёвый коуч с экраном – тот, что семплирует кадры только тогда, когда транскрипция намекает на важность экрана, а не по фиксированному частому таймеру. Эту поэлементную экономику мы моделируем в реальной стоимости ИИ в видео-продуктах, а компромиссы в том, как часто и насколько подробно семплировать кадры, – целиком тема урока Video VLMs – семплирование кадров против потока токенов.

Вторая оговорка – понятность. Неподвижный кадр слайда модель воспринимает легко; кадр на середине прокрутки или во время быстрого демо может получиться размытым и неинформативным. Кроме того, содержимое экрана зачастую очень детализировано – мелкий текст, плотные таблицы, – и при уменьшении до 1024 пикселей такой текст может исчезнуть. Для коуча это обычно не проблема, ведь важна суть («на экране таблица с ценами»), а не мелкий шрифт; но если когда-нибудь понадобится прочитать именно мелкий текст, сделайте снимок одного кадра в более высоком разрешении – за это придётся заплатить больше.

Способность третья: передать коучу ваш плейбук

Инструменты позволяют коучу быстро находить нужную информацию по запросу. Но ему также нужны общие, постоянно доступные знания – ваша методология, сведения о продукте, позиционирование относительно конкурентов, – которые должны присутствовать в каждой подсказке без необходимости каждый раз обращаться к инструментам. Эти базовые знания обеспечивает генерация с дополнением поиском (RAG), а рекомендации LiveKit по работе с внешними данными помогают подключить их так, чтобы не замедлять ход звонка.

Начните с разделения двух типов знаний по частоте их обновления. Методология продаж и факты о продукте одинаковы для каждого звонка – их можно загрузить один раз при запуске процесса агента. LiveKit называет этот этап prewarm – и именно здесь такие данные следует хранить, чтобы использовать повторно на всех звонках, обслуживаемых этим процессом.

На другом конце шкалы – данные, специфичные для конкретного звонка: кто ведёт разговор, какой аккаунт участвует, что обсуждалось на предыдущем звонке. Эти сведения не должны попадать в prewarm, а должны передаваться агенту как метаданные звонка при его диспетчеризации. LiveKit позволяет прикреплять их либо как job metadata, либо как participant attributes. Явная рекомендация: отправляйте данные по конкретному звонку именно в метаданных, а не загружайте их внутри стартового пути агента. Если же требуется сетевой вызов при старте – выполняйте его до подключения агента к комнате, чтобы менеджер не увидел коуча раньше, чем тот действительно готов.

Именно здесь поступает идентификация менеджера – тот самый destination_identity с рис. 1, – чтобы коуч знал, кому следует давать подсказки.

Между этими двумя полюсами – живой поиск: пока клиент говорит, подтягивается самый релевантный фрагмент вашего плейбука, соответствующий только что сказанному. Сделать это можно двумя способами, и выбор между ними – ключевое различие между быстрым и медлительным коучем. Мы уже видели способ с вызовом инструмента: модель сама решает, когда вызвать get_battlecard, но это требует дополнительного обращения к модели. Более быстрый подход – использовать конвейер «распознавание – затем модель»: поиск по реплике пользователя выполняется до запуска модели, а результат сразу вставляется в её контекст. LiveKit реализует это через хук on_user_turn_completed, и в документации прямо указано преимущество: такой способ исключает лишние вызовы, связанные с инструментами, потому что поиск происходит на том же этапе, что и обработка реплики, а не как отдельный запрос, который модель должна инициировать и ждать. Компромисс в том, что вы отказываетесь от решения модели о необходимости поиска – он выполняется всегда. Поэтому этот подход лучше всего подходит для задач, которые нужно выполнять на каждой реплике, например: «найти в плейбуке самый релевантный фрагмент к только что сказанному».

Простое эвристическое правило: используйте вставку на завершённой реплике для широкого контекста плейбука на каждом ходу, а явные инструменты оставляйте для точных, нечастых действий – подтянуть один конкретный аккаунт, проверить одну скидку, записать результат в CRM. Урок по video RAG по архиву углубляется в саму сторону поиска; здесь же речь идёт лишь о том, где в цикле звонка каждый вид знаний применяется.

Складываем вместе: цикл коуча

Теперь у нас есть все компоненты. Отойдите на шаг назад и посмотрите, как проходит один полный цикл – ведь архитектура – это просто эти части, собранные в правильном порядке.

Рис. 4. Весь коуч как рантайм. Три входа – речь, экран, плейбук – питают один цикл модели; один приватный выход доходит до менеджера в одиночку.

Клиент формулирует предложение. Транскрайбер, обрабатывающий одну сессию на говорящего – такой же подход, как у ноутейкера, с одной сессией распознавания на участника, чтобы каждая строка была атрибутирована, – выдаёт финальную строку, привязанную к клиенту. На основе этой завершённой реплики коуч извлекает наиболее релевантный фрагмент из плейбука, вставляет его, прикрепляет актуальный кадр экрана и запускает модель. Модель может потребовать конкретный факт и вызвать соответствующий инструмент; если инструмент работает медленно, он выполняется в фоне, не нарушая отзывчивости цикла. Модель формирует краткую подсказку. Коуч отправляет её через RPC-вызов менеджеру, и приватная панель менеджера обновляется. Клиент всё это время ничего не слышал и не видел, кроме менеджера.

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

Строить это или купить надстройку для коучинга?

Коучинг в реальном времени – уже полноценная категория продуктов, поэтому честное сравнение идёт не между «сделать самому» и «купить», а между покупкой и самостоятельной разработкой. Устоявшиеся вендоры conversation intelligence и новые инструменты реального времени предлагают живые баттлкарты, подсказки по возражениям и сигналы о пропущенных вопросах во время звонков. Ключевой сдвиг на этом рынке в 2026 году – переход к «агентному» коучингу, который не просто фиксирует моменты, но и автоматически составляет письмо-фоллоуап и обновляет CRM после звонка. Если вам нужен коучинг, интегрированный с текущими звонками менеджеров в Zoom или Meet, и он не должен быть встроен в ваш продукт – покупка будет быстрее.

Версию на LiveKit вы выбираете, когда коучинг должен быть интегрирован в программное обеспечение, которым вы уже владеете – ваше приложение для видеоконференций, телемедицинскую платформу, e-learning-комнату или инструмент для продаж, который вы поставляете клиентам, – или когда плейбуки, модели и данные звонков должны оставаться на инфраструктуре, которую вы контролируете. Это та же логика «строить или покупать», что и у ноутейкера, но на ступень выше по возможностям.

ПутьЧто вы делаетеКогда лучше
Строить на LiveKit (этот урок)Запускаете агента-коуча в своей комнатеКоучинг живёт в вашем продукте; вы владеете данными и плейбуком
LiveKit на своём хостингеЗапускаете open-source сервер и агентаЖёсткие требования к приватности, резидентности данных, on-prem
Купить инструмент коучингаПодключаете его к звонкам менеджеров в Zoom/MeetКоучинг – надстройка к звонкам, которыми вы не владеете

Структура издержек при построении системы расширяет расходы ноутейкера. Те же три счётчика LiveKit – минуты участников WebRTC для всех в комнате, включая агента; минуты сессии агента за его собственный рантайм; и распознавание речи за минуту аудио. Коуч добавляет два счётчика модели, которых ноутейкер в основном избегал: текстовые токены за непрерывное мышление и vision-токены за каждый семплированный кадр экрана. Ноутейкер запускает одну модель в конце звонка; коуч запускает её многократно в ходе разговора. Это цена действия в реальном времени, а частота семплирования с рис. 3 – ваш главный регулятор vision-части этих затрат.

«Частая ошибка: коуч, который «протекает», «блокирует» или «достаёт». Три режима отказа – основная причина сбоев у коучей. Первый – утечка: у агента включён аудиовыход или он рассылает советы всем в комнате, и клиент видит плейбук. Решение: не публиковать аудио и отправлять подсказки только через адресный RPC одному получателю, как показано на рис. 1. Второй – блокировка: медленный инструмент CRM тормозит цикл, и коуч отстаёт от разговора. Решение: запускать сетевые инструменты в фоне и не блокировать основной цикл. Третий – занудство: коуч выдаёт подсказку после каждой реплики, менеджер перегружен и отключает панель. Решение: повысить порог для прерывания в инструкциях модели и ограничить частоту подсказок в коде – не чаще одной за несколько секунд. Коуч, который молчит 90% времени и точен в оставшиеся 10%, – тот, кого менеджеры оставляют включённым.»

Пара слов о согласии и законе

Поскольку коуч обрабатывает речь и экран клиента в реальном времени, он попадает под законы о записи разговоров и раскрытии ИИ – и эти аспекты нужно закладывать с самого начала, а не добавлять потом. В нескольких штатах США требуется согласие всех участников звонка на его запись или мониторинг; в Европейском союзе правила прозрачности по AI Act обязывают информировать людей, когда они взаимодействуют с системой ИИ или подвергаются её обработке – в большинстве контекстов.

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

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

Детали инженерной реализации раскрытия для ИИ-функций описаны в уроке про статью 50 EU AI Act.

Где здесь Фора Софт

Мы разрабатываем продукты для видеосвязи в реальном времени с 2005 года – видеоконференции, телемедицину, e-learning и совместную работу в режиме реального времени – и агент встреч стал почти стандартным требованием в проектах, которые мы оцениваем. Коуч – это более продвинутая версия этого запроса: тот же участник «слушать и смотреть», но теперь с возможностью вызывать инструменты в CRM и использовать плейбук клиента, а также с приватным каналом связи с одним пользователем. Архитектура, описанная в этом уроке, – та, к которой мы обращаемся, когда коучинг должен быть интегрирован непосредственно в продукт клиента, а не реализован через сторонний сервис, подключённый к Zoom. В телемедицине тот же паттерн приватной подсказки превращается в подсказку врачу во время приёма; в e-learning – в тихую подсказку преподавателю; в продажах – в описанного здесь коуча. Ключевое инженерное соображение для нас: в первую очередь – правило приватности, во вторую – бюджет задержки, в третью – регулятор издержек – частота семплирования.

Главное

  • Коуч продаж – это ноутейкер, усиленный тремя чувствами: способность вызывать инструменты, зрение экрана и приватный канал общения.
  • Непреложное правило: совет по RPC должен доставляться только менеджеру – ни в виде аудио в общую комнату, ни как широковещательное сообщение.
  • Docstrings инструментов – это инструкции, которым следует модель; описывайте не только «что вернёт», но и «когда использовать».
  • Запускайте медленные инструменты в фоне, чтобы коуч не отставал от живого диалога.
  • Семплируйте именно трек демонстрации экрана, а не самое свежее видео; частота семплирования – ваш регулятор издержек.
  • Коучинг в реальном времени регулируется: раскрывайте использование ИИ, получайте согласие и согласовывайте правила с юристом.

Что почитать дальше

Строите такую систему?

Подберём параметры кодирования под ваш контент и посчитаем стоимость доставки до старта разработки.