Felo API PlatformFelo API Platform

Поддержка

Разберите тикет поддержки в обоснованный черновик ответа

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

Время20 минутУровеньСреднийОбновлено2026-10-30
Для когоРуководители поддержкиHelpdesk AgentИнженеры поддержки

Скопировать промпт

Замените поля в квадратных скобках и вставьте в Claude Code, Codex или любой AI с доступом к терминалу. Он установит навык Felo, спросит перед списанием кредитов и выполнит процесс.

Разбери этот тикет поддержки и подготовь черновик ответа для проверки человеком: [вставь тикет, удалив имя, email, ID аккаунта, платёжные данные и любую идентифицирующую информацию].

Область продукта: [продукт]. План или регион: [только если нужно для ответа]. Источник документации: [URL справочного центра или LiveDoc short_id].
Путь согласования: [кто проверяет]. Очередь эскалации: [команда или канал].

Подготовь:
1. Намерение: одну категорию и одно предложение обоснования.
2. Приоритет: срочный / обычный / низкий, с применённым правилом.
3. Доказательства: фрагменты документации, которые отвечают на тикет, с названием и релевантностью.
4. Проверку инцидента: указывают ли публичные сообщения на массовый сбой. Ссылка и дата или «публичных сигналов нет».
5. Маршрут: черновик, запрос дополнительной информации или эскалация — и почему.
6. Черновик ответа: два-четыре предложения, только на основе доказательств, с указанием использованного источника.

Правила:
- Не помещай имена, email, номера заказов, токены и платёжные данные в вызовы API или вывод. Работай только с обезличенным тикетом.
- Отвечай только по найденной документации. Без доказательств эскалируй, а не угадывай.
- Не обещай возврат, скидку, сроки или изменение аккаунта; такие случаи передавай на эскалацию.
- Публичные слухи о сбое — это сигнал, а не доказательство. Цитируй пост и дату.
- Перед расходом кредитов покажи планируемые вызовы и дождись моего одобрения.
- Не отправляй ответ, не обновляй тикет и не выполняй действия с аккаунтом. Верни черновик на проверку.
- Запиши результат в ./support-triage.md и кратко изложи его в чате.

В копию также входят шаги установки и правила безопасности.

Что получится

Пример вывода одного запуска. Не живая генерация.

Пример триажа (фрагмент)

Триаж — пример тикета

Намерение

Вопрос об оплате / продлении. Клиент спрашивает, почему план снова продлился.

Приоритет

Обычный. Это вопрос оплаты, не сбой, клиент не заблокирован.

Доказательства

  • «частые вопросы по оплате» — срок продления и повторы при ошибке карты. Релевантность: высокая.
  • «Изменения плана» — понижение между продлениями. Релевантность: средняя.

Проверка инцидентов

Публичных сообщений за последние 48 часов нет.

Маршрут

Черновик. Документация покрывает вопрос.

Черновик ответа

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

Заметка ревьюеру

Одобрить, отредактировать или эскалировать в очередь оплаты.

Реальные вызовы

Для разработчиков: тот же процесс в виде кода в порядке выполнения.

Показать реальные вызовы API
  1. Замаскируйте и классифицируйте

    Кодом удалите email, телефоны и номера заказов, затем через Chat определите намерение и приоритет.

    triage.ts
    const BASE = "https://openapi.felo.ai";
    const headers = {
      Authorization: `Bearer ${process.env.FELO_API_KEY}`,
      "Content-Type": "application/json",
    };
    
    async function felo<T>(path: string, body?: unknown): Promise<T> {
      const res = await fetch(`${BASE}${path}`, {
        method: body ? "POST" : "GET",
        headers,
        body: body ? JSON.stringify(body) : undefined,
      });
      if (!res.ok) throw new Error(`${res.status}: ${await res.text()}`);
      return res.json() as Promise<T>;
    }
    
    const redact = (text: string) =>
      text
        .replace(/[\w.+-]+@[\w.-]+\.\w+/g, "[email]")
        .replace(/\b(?:acct|account|order|invoice)[-_ ]?\w+\b/gi, "[id]")
        .replace(/\b(?:\d[ -]?){13,19}\b/g, "[card]");
    
    type Ticket = {
      id: string;
      product: string;
      subject: string;
      body: string;
      plan?: string;
      sensitive?: boolean;
    };
    
    const ticket: Ticket = {
      id: "T-1042",
      product: "Acme Workspace",
      subject: "Why did my plan renew?",
      body: "I was charged again and cannot find the renewal date on my account.",
      plan: "team",
    };
    
    const summary = redact(`${ticket.subject}\n\n${ticket.body}`).slice(0, 1500);
    
    type ChatData = {
      data: {
        answer: string;
        resources: { link: string; title: string; snippet: string }[];
      };
    };
    
    const triage = await felo<ChatData>("/v2/chat", {
      query: `Classify this support question by intent and priority, and list what is missing:\n\n${summary}`,
    });
    
    console.log(triage.data.answer);

    Пример вывода

    {
      "answer": "Intent: billing / renewal question. Priority: normal. Missing: the renewal date the customer expects.",
      "resources": [
        { "link": "https://example.com/billing-faq", "title": "Billing FAQ", "snippet": "…" }
      ]
    }
  2. Найдите доказательства в документации

    Ищите релевантные фрагменты в LiveDoc базы знаний, сохраняя заголовки и оценки.

    triage.ts
    type Hit = { title: string; content: string; score: number };
    
    const KB = process.env.SUPPORT_LIVEDOC_ID!; // the help-center LiveDoc short_id
    
    const retrieved = await felo<{ data: Hit[] }>(
      `/v2/livedocs/${KB}/resources/retrieve`,
      { query: summary },
    );
    
    const hits = retrieved.data.filter((hit) => hit.score >= 0.7).slice(0, 4);
    
    if (hits.length === 0) {
      console.log("No grounded evidence: escalate instead of drafting");
    }

    Пример вывода

    [
      {
        "title": "Billing FAQ",
        "content": "Your plan renews on the first of the month; a failed card retries for three days…",
        "score": 0.91
      }
    ]
  3. Проверьте публичный инцидент

    Ищите в X название продукта и слова «сбой/недоступен» за 48 часов, используя только как публичный сигнал.

    triage.ts
    type XData = {
      data: {
        tweets: {
          content: string;
          author: { username: string };
          created_at: string;
          url: string;
        }[];
      };
    };
    
    const since = Math.floor((Date.now() - 48 * 60 * 60 * 1000) / 1000);
    
    const incident = await felo<XData>("/v2/x/tweet/search", {
      query: `"${ticket.product}" (outage OR "not working" OR error)`,
      limit: 20,
      since_time: since,
    });
    
    const reports = incident.data.tweets.map((post) => ({
      text: post.content,
      handle: post.author.username,
      at: post.created_at.slice(0, 10),
      link: post.url,
    }));

    Пример вывода

    [
      {
        "text": "Workspace login is failing for my whole team.",
        "handle": "example_user",
        "at": "2026-10-30",
        "link": "https://x.com/example_user/status/..."
      }
    ]
  4. Определите маршрут и соберите ответ

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

    triage.ts
    type Route = "draft" | "ask-customer" | "escalate";
    
    function decideRoute(): { route: Route; reason: string } {
      if (hits.length === 0) {
        return { route: "escalate", reason: "no grounded evidence in the knowledge base" };
      }
      if (ticket.sensitive) {
        return { route: "escalate", reason: "an account or billing action is requested" };
      }
      if (reports.length >= 3) {
        return { route: "escalate", reason: "public reports suggest a wider issue" };
      }
      if (!ticket.plan) {
        return { route: "ask-customer", reason: "the plan is needed to answer the question" };
      }
      return { route: "draft", reason: "the documentation covers the question" };
    }
    
    const decision = decideRoute();
    
    const packet = [
      `# Triage — ${ticket.id}`,
      "",
      `Route: ${decision.route} (${decision.reason})`,
      "",
      "## Intent and priority",
      triage.data.answer,
      "",
      "## Evidence",
      ...hits.map((hit) => `- ${hit.title} (score ${hit.score})`),
      "",
      "## Public signal",
      ...(reports.length
        ? reports.map((report) => `- @${report.handle} (${report.at}): ${report.text} — ${report.link}`)
        : ["No public reports in the last 48 hours."]),
      "",
      "## Reply draft",
      "[Written by the host Agent from the evidence above — human review required]",
    ].join("\n");
    
    console.log(packet);

    Пример вывода

    # Triage — T-1042
    
    Route: draft (the documentation covers the question)
    
    ## Intent and priority
    Intent: billing / renewal question. Priority: normal.
    
    ## Evidence
    - Billing FAQ (score 0.91)
  5. Запишите триаж

    Запишите результат триажа в LiveDoc для разбора и аудита.

    triage.ts
    type LiveDocData = { data: { short_id: string } };
    
    const log = await felo<LiveDocData>("/v2/livedocs", {
      name: "Support triage log",
      description: "One document resource per triaged ticket",
    });
    
    await felo(`/v2/livedocs/${log.data.short_id}/resources/doc`, {
      title: `Triage — ${ticket.id}`,
      content: packet,
    });
    
    console.log(log.data.short_id); // reuse it for the next ticket

    Пример вывода

    { "short_id": "PvyKouzJirXjFdst4uKRK3" }

Что входит

  • Классификация намерения и приоритета после маскировки
  • Доказательства из документации с оценками
  • Проверка публичного инцидента
  • Черновик ответа с маршрутизацией
  • LiveDoc с записью триажа

Чего не делает

  • Не отправляет ответ, не закрывает тикет и не выполняет действия с аккаунтом
  • Не отправляйте в API пароли, платёжные данные и полные данные клиента
  • При отсутствии попаданий в документацию обязательна эскалация
  • X — сигнал публичного инцидента, а не состояние системы поддержки
  • Правила приоритета задаёте вы, модель только предлагает

Вопросы

Какие данные тикета можно отправлять?

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

Откуда берётся ответ?

Из фрагментов, найденных в LiveDoc документации. Если попаданий нет, процесс эскалирует, а не угадывает.

Он сам отвечает или закрывает тикет?

Нет. Он создаёт только черновик и маршрут; отправку и закрытие выполняет человек или ваша система.

Как определяется приоритет?

Вашими правилами; модель предлагает решение и причину, а итоговый приоритет подтверждает маршрутизация.

Что если документация не покрывает вопрос?

Эскалация в очередь к человеку с пометкой «не покрыто» в пакете триажа.

Сколько стоит триаж?

Chat, поиск и X Search оплачиваются по факту использования; актуальные тарифы на странице цен, промпт просит одобрение до трат.

Связанные процессы

Адаптируйте под себя

Тот же рецепт, подстроенный под ваш реальный процесс.

Только классификация

Без ответа: только намерение, приоритет и рекомендуемая очередь.

Подключите тикет-систему

Через свой webhook запишите пакет в тикет, не отправляя ответ автоматически.

Передайте в базу знаний

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

Справочные страницы этого рецепта и куда двигаться дальше.