Как отправить именованные ссылки в Telegram из 1С?

Программист 1С v8.3 (Управляемые формы) IT и автоматизация бизнеса
← На главную

При интеграции 1С с Telegram Bot API часто возникает задача отправки сообщений, содержащих ссылки не в виде простого URL, а с пользовательским наименованием. Это значительно улучшает читаемость и пользовательский опыт. Рассмотрим, как мы можем реализовать эту функциональность в 1С, используя различные подходы, такие как разметка MarkdownV2, HTML, а также более детальное форматирование через механизм entities. Мы также затронем аспект добавления интерактивных кнопок с ссылками.

Основное решение: Отправка ссылок с использованием parse_mode=MarkdownV2

Наиболее универсальным и рекомендуемым способом является отправка сообщения с параметром parse_mode=MarkdownV2. В этом режиме Telegram интерпретирует специальный синтаксис для форматирования текста, включая именованные ссылки.

Формат именованной ссылки в MarkdownV2

В MarkdownV2 именованная ссылка имеет вид: [ИмяСсылки](URL_ссылки). Важно помнить, что ИмяСсылки и URL_ссылки должны быть строковыми значениями.

Формирование одной ссылки

Давайте посмотрим, как мы можем сформировать одну именованную ссылку в 1С:


// Предположим, у нас есть строковые переменные с наименованием и URL
СтрокаНазвание = "Напишите нам в бот в Щелково";
СтрокаURL = Контакты1.ТГЩелково; // Получаем URL из какого-либо источника, например, справочника

// Формируем текст сообщения с использованием синтаксиса MarkdownV2
ТекстСообщения = "[" + СтрокаНазвание + "]" + "(" + СтрокаURL + ")";

// Вставляем сформированный текст в структуру сообщения для Telegram
СтруктураСообщения.Вставить("text", ТекстСообщения);
// Обязательно указываем режим разметки
СтруктураСообщения.Вставить("parse_mode", "MarkdownV2");

Обратите внимание на правильную расстановку квадратных и круглых скобок. В квадратных скобках указывается наименование ссылки, а в круглых – сам URL.

Формирование нескольких ссылок из табличной части

Если нам необходимо отправить несколько ссылок, которые хранятся, например, в табличной части справочника, мы можем сформировать одну общую строку, объединяя каждую ссылку с новой строки с помощью Символы.ПС.


// Предположим, "Ссылка" - это табличная часть, содержащая колонки "ИмяСсылки" и "СсылкаНаСайт"
СсылкаНаФото = Справочники.ПользовательскиеПоля.НайтиПоКоду("000000001");
Ссылка = СсылкаНаФото.СсылкиНаФотографии; // Пример получения табличной части

СсылкиТекст = ""; // Инициализируем пустую строку для сбора всех ссылок

Для каждого Элемент из Ссылка Цикл
    // Каждую ссылку форматируем и добавляем в общую строку,
    // разделяя их символом перевода строки для лучшей читаемости в Telegram
    СсылкиТекст = СсылкиТекст + "[" + Элемент.ИмяСсылки + "]" + "(" + Элемент.СсылкаНаСайт + ")" + Символы.ПС;
КонецЦикла;

// Вставляем сформированный текст в структуру сообщения
СтруктураСообщения.Вставить("text", СсылкиТекст);
// Обязательно указываем режим разметки
СтруктураСообщения.Вставить("parse_mode", "MarkdownV2");

Таким образом, мы получим сообщение со списком именованных ссылок, каждая из которых будет отображена на новой строке.

Отправка сообщения в Telegram

После того как структура сообщения сформирована, мы отправляем ее в Telegram Bot API. Мы будем использовать HTTPСоединение и HTTPЗапрос для этого.

  1. Создаем структуру сообщения: В эту структуру мы помещаем все необходимые параметры, такие как chat_id, text и parse_mode.
  2. Сериализуем структуру в JSON: Telegram Bot API ожидает тело запроса в формате JSON.
  3. Отправляем POST-запрос: Мы используем метод POST для отправки JSON-тела.

Процедура ОтправитьСообщениеВТелеграм(ЧатID, СтруктураСообщения, КлючАПИ) Экспорт
    Сервер = "api.telegram.org";
    Соединение = Новый HTTPСоединение(Сервер,,,,,,Новый ЗащищенноеСоединениеOpenSSL);
    
    Запрос = Новый HTTPЗапрос;
    Команда = "sendMessage";
    
    // Добавляем обязательные параметры в структуру сообщения, если их там еще нет
    Если Не СтруктураСообщения.Свойство("chat_id") Тогда
        СтруктураСообщения.Вставить("chat_id", ЧатID);
    КонецЕсли;
    Если Не СтруктураСообщения.Свойство("parse_mode") Тогда
        // По умолчанию используем MarkdownV2, если не указано другое
        СтруктураСообщения.Вставить("parse_mode", "MarkdownV2");
    КонецЕсли;

    // Сериализуем структуру в JSON-строку
    JSONСериализатор = Новый ЗаписьJSON;
    JSONСериализатор.УстановитьСтроку();
    ЗаписатьJSON(JSONСериализатор, СтруктураСообщения);
    СтрокаПоПараметрам = JSONСериализатор.Закрыть();
    
    Запрос.Заголовки.Вставить("Content-Type","application/json");
    Запрос.УстановитьТелоИзСтроки(СтрокаПоПараметрам, "UTF-8"); // Важно использовать UTF-8
    
    Ресурс = "bot" + КлючАПИ + "/" + Команда;
    Запрос.АдресРесурса = Ресурс;
    
    Попытка
        Ответ = Соединение.Отправить(Запрос); // Отправляем POST запрос
        Если Ответ.КодСостояния = 200 Тогда
            Сообщить("Сообщение успешно отправлено.");
        Иначе
            Сообщить("Ошибка отправки сообщения: " + Ответ.КодСостояния + " " + Ответ.ПолучитьТелоКакСтроку());
        КонецЕсли;
    Исключение
        Сообщить("Ошибка HTTP-соединения: " + ОписаниеОшибки());
    КонецПопытки;
    
    Соединение = Неопределено;
    Запрос = Неопределено;
КонецПроцедуры

// Пример вызова:
// МойЧатID = "ВАШ_CHAT_ID";
// МойКлючАПИ = "ВАШ_КЛЮЧ_API";
// СтруктураСообщенияДляОтправки = Новый Структура("text", "Это [пример](https://example.com) ссылки.");
// ОтправитьСообщениеВТелеграм(МойЧатID, СтруктураСообщенияДляОтправки, МойКлючАПИ);

Важно: При использовании parse_mode=MarkdownV2, если в тексте сообщения или имени ссылки присутствуют специальные символы Markdown (такие как _, *, [, ], (, ), ~, `, >, #, +, -, =, |, {, }, ., !), их необходимо экранировать обратным слэшем \, если они не являются частью синтаксиса разметки. Например, для текста "Мой_Документ.pdf" нужно отправить "Мой\_Документ\.pdf".

Альтернативное решение: Отправка ссылок с использованием parse_mode=HTML

Вторым распространенным способом является использование parse_mode=HTML. В этом случае Telegram интерпретирует стандартные HTML-теги для форматирования текста, включая ссылки.

Формат именованной ссылки в HTML

В HTML именованная ссылка оформляется как стандартный тег: <a href="URL_ссылки">ИмяСсылки</a>.

Формирование ссылки в 1С с HTML-разметкой

При формировании HTML-строки в 1С необходимо тщательно следить за экранированием кавычек.


// Предположим, у нас есть строковые переменные с наименованием и URL
СтрокаНазвание = "Наш сайт";
СтрокаURL = "https://www.example.com";

// Формируем текст сообщения с использованием синтаксиса HTML
// Обратите внимание на удвоенные кавычки для экранирования внутри строкового литерала 1С
ТекстСообщения = "<a href=""" + СтрокаURL + """>" + СтрокаНазвание + "</a>";

// Вставляем сформированный текст в структуру сообщения для Telegram
СтруктураСообщения.Вставить("text", ТекстСообщения);
// Обязательно указываем режим разметки
СтруктураСообщения.Вставить("parse_mode", "HTML");

Формирование нескольких ссылок из табличной части с HTML

Аналогично Markdown, мы можем собрать несколько HTML-ссылок из табличной части.


// Предположим, "Ссылка" - это табличная часть
СсылкаНаФото = Справочники.ПользовательскиеПоля.НайтиПоКоду("000000001");
Ссылка = СсылкаНаФото.СсылкиНаФотографии;

СсылкиТекст = ""; // Инициализируем пустую строку

Для каждого Элемент из Ссылка Цикл
    // Формируем каждую ссылку в HTML-формате, экранируя кавычки
    СсылкиТекст = СсылкиТекст + "<a href=""" + Элемент.СсылкаНаСайт + """>" + Элемент.ИмяСсылки + "</a>" + Символы.ПС;
КонецЦикла;

// Вставляем сформированный текст в структуру сообщения
СтруктураСообщения.Вставить("text", СсылкиТекст);
// Обязательно указываем режим разметки
СтруктураСообщения.Вставить("parse_mode", "HTML");

Механизм entities: Гибкий, но более сложный подход

Telegram Bot API также предоставляет возможность тонкой настройки форматирования текста с помощью массива entities. Каждая "сущность" (entity) описывает определенный фрагмент текста (например, ссылку, жирный текст, курсив) путем указания его типа, смещения (offset) от начала сообщения и длины (length).

Принцип работы entities для ссылок

Для именованной ссылки через entities мы указываем:

  1. type: "text_link"
  2. offset: Начальная позиция (индекс с 0) текста, который является ссылкой.
  3. length: Длина этого текста.
  4. url: Сам URL-адрес ссылки.

Пример использования entities в 1С


// Сначала формируем полный текст сообщения
ТекстСообщения = "Это ссылка на сайт Infostart.";
СтруктураСообщения.Вставить("text", ТекстСообщения);

// Создаем структуру для сущности (entity) типа "text_link"
СтруктураURL = Новый Структура("url", "https://www.infostart.ru");
СтруктураURL.Вставить("type", "text_link");
// Определяем смещение и длину слова "ссылка" в тексте "Это ссылка на сайт Infostart."
// "ссылка" начинается с 4-го символа (индексация с 0) и имеет длину 6 символов.
СтруктураURL.Вставить("offset", 4); 
СтруктураURL.Вставить("length", 6); 

// Добавляем сущность в массив
МассивURL = Новый Массив;
МассивURL.Добавить(СтруктураURL);

// Прикрепляем массив сущностей к сообщению
СтруктураСообщения.Вставить("entities", МассивURL);

// В этом случае parse_mode не требуется, так как форматирование задано явно через entities.
// Однако, если есть другая разметка (например, жирный текст), parse_mode может быть использован для нее.

Недостатки entities: Основная сложность этого подхода заключается в необходимости точного расчета offset и length. При динамическом изменении текста или наличии нескольких ссылок, особенно из табличной части, этот метод становится значительно более трудоемким по сравнению с использованием parse_mode=MarkdownV2 или parse_mode=HTML. Поэтому для большинства случаев предпочтительнее использовать именно режимы разметки.

Дополнительный функционал: Добавление кнопок с ссылками (Inline Keyboard)

Иногда требуется не просто вставить ссылку в текст, а создать интерактивную кнопку под сообщением, которая при нажатии открывает определенный URL. Для этого используются "inline-кнопки" через параметр reply_markup.

Пример добавления кнопки с ссылкой

Мы формируем JSON-структуру для reply_markup, которая содержит массив inline_keyboard, а внутри него — массив кнопок. Каждая кнопка может иметь тип url, указывающий на открываемую ссылку.


// Сначала формируем обычное текстовое сообщение
СтруктураСообщения.Вставить("text", "Нажмите кнопку, чтобы перейти на сайт:");

// Создаем структуру для inline-клавиатуры
СтруктураКлавиатуры = Новый Структура;
МассивРядовКнопок = Новый Массив; // Массив для рядов кнопок

// Создаем ряд кнопок (можно несколько)
МассивКнопокВРяду = Новый Массив;

// Создаем отдельную кнопку
СтруктураКнопки = Новый Структура;
СтруктураКнопки.Вставить("text", "Перейти на InfoStart"); // Текст на кнопке
СтруктураКнопки.Вставить("url", "https://www.infostart.ru"); // URL, который откроется при нажатии

МассивКнопокВРяду.Добавить(СтруктураКнопки); // Добавляем кнопку в ряд
МассивРядовКнопок.Добавить(МассивКнопокВРяду); // Добавляем ряд кнопок в общую клавиатуру

СтруктураКлавиатуры.Вставить("inline_keyboard", МассивРядовКнопок);

// Вставляем структуру клавиатуры в общее сообщение
СтруктураСообщения.Вставить("reply_markup", СтруктураКлавиатуры);

// Для такого сообщения parse_mode может быть любым или отсутствовать,
// если в самом тексте нет другой разметки.

Таким образом, под вашим сообщением появится кнопка, которая при нажатии перенаправит пользователя по указанному URL.

Важные моменты и рекомендации

  1. Токен бота: Убедитесь, что вы используете корректный токен вашего бота, полученный от BotFather. Он имеет формат 1111:AAABBBCCCDDDEEEFFFGGGHHHIIIJJJKKKLLL.
  2. Chat ID: Всегда передавайте правильный chat_id пользователя или группы, куда отправляется сообщение.
  3. Кодировка UTF-8: При работе с HTTPЗапрос.УстановитьТелоИзСтроки() критически важно указывать кодировку "UTF-8", чтобы избежать проблем с отображением русских и других специальных символов.
  4. Экранирование символов: Как уже упоминалось, при использовании parse_mode=MarkdownV2 будьте внимательны к специальным символам, которые могут требовать экранирования.
  5. Структура кода: Для поддержания читаемости и облегчения отладки рекомендуется оформлять логику формирования и отправки сообщений в отдельные процедуры или функции.

Применяя эти методы, мы сможете эффективно отправлять информативные и интерактивные сообщения в Telegram из вашей системы 1С.

← На главную