Парсер сущностей (entity-parser )
Преобразует сущности Telegram в семантический HTML.
Когда стоит это использовать?
Вероятно, НИКОГДА!
Хотя этот плагин может генерировать HTML, в большинстве случаев лучше передавать текст и сущности обратно в Telegram.
Преобразование в HTML требуется только в редких случаях, например, если вам нужно использовать текст с форматированием Telegram вне самого Telegram, например, для отображения сообщений на сайте.
Посмотрите раздел Случаи, когда лучше не использовать этот пакет, чтобы понять, сталкиваетесь ли вы с аналогичной задачей.
Если вы не уверены, подходит ли этот плагин для вашего случая, не стесняйтесь задавать вопросы в наших англоязычном и русскоязычном чатах. В большинстве случаев выясняется, что для решения ваших задач этот плагин не нужен!
Уставнока
Выполните следующую команду в вашем терминале, исходя из используемого пакетного менеджера:
deno add jsr:@qz/telegram-entities-parserbunx jsr add @qz/telegram-entities-parserpnpm dlx jsr add @qz/telegram-entities-parseryarn dlx jsr add @qz/telegram-entities-parsernpx jsr add @qz/telegram-entities-parserПростое использование
Использовать этот плагин очень просто. Вот краткий пример:
import { EntitiesParser } from "@qz/telegram-entities-parser";
import type { Message } from "@qz/telegram-entities-parser/types";
// Для повышения производительности создайте парсер вне функции.
const entitiesParser = new EntitiesParser();
const parse = (message: Message) => entitiesParser.parse({ message });
bot.on(":text", (ctx) => {
const html = parse(ctx.msg); // Преобразует текст в строку HTML
});
bot.on(":photo", (ctx) => {
const html = parse(ctx.msg); // Преобразует подпись к фото в строку HTML
});2
3
4
5
6
7
8
9
10
11
12
13
14
Расширенное использование
Настройка выходного HTML тега
Этот пакет преобразует сущности в семантический HTML, следуя лучшим практикам и стандартам настолько близко, насколько это возможно. Однако предоставленный результат может не всегда соответствовать вашим ожиданиям.
Чтобы это исправить, вы можете использовать собственный renderer для настройки HTML тегов, окружающих текст, в соответствии с вашими правилами. Вы можете изменить конкретные правила, расширив стандартный Renderer, или переопределить все правила, реализовав собственный Renderer.
Чтобы расширить существующий renderer, выполните следующие шаги:
import { EntitiesParser, RendererHtml } from "@qz/telegram-entities-parser";
import type {
CommonEntity,
RendererOutput,
} from "@qz/telegram-entities-parser/types";
// Изменение правила для жирного текста,
// оставив остальные типы, определенные в `RendererHtml`.
class MyRenderer extends RendererHtml {
override bold(
options: { text: string; entity: CommonEntity },
): RendererOutput {
return {
prefix: '<strong class="tg-bold">',
suffix: "</strong>",
};
}
}
const entitiesParser = new EntitiesParser({ renderer: new MyRenderer() });2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
Параметр options принимает объект с полями text и entity.
text: Конкретный текст, к которому относится текущая сущность.entity: Может быть представлен различными интерфейсами в зависимости от типа сущности, такими какCommon,Entity Custom,Emoji Entity Pre,Entity TextилиLink Entity Text. Например, сущность типаMention Entity boldимеет интерфейсCommon, тогда как типEntity textможет иметь интерфейс_link Text, так как включает дополнительные свойства, такие какLink Entity url.
Вот полный список интерфейсов и выходных данных для каждого типа сущности:
| Тип сущности | Интерфейс | Результат |
|---|---|---|
blockquote | Common | <blockquote class |
bold | Common | <b class |
bot | Common | <span class |
cashtag | Common | <span class |
code | Common | <code class |
custom | Custom | <span class |
email | Common | <a class |
expandable | Common | <blockquote class |
hashtag | Common | <span class |
italic | Common | <i class |
mention | Common | <a class |
phone | Common | <a class |
pre | Pre | <pre class или <pre class |
spoiler | Common | <span class |
strikethrough | Common | <del class |
text | Text | <a class |
text | Text | <a class или <a class |
underline | Common | <span class |
url | Common | <a class |
Если вы не уверены, какой интерфейс использовать, обратитесь к реализации Renderer или Renderer
Настройка санитайзера текста
Выводимый текст по умолчанию проходит санитизацию для обеспечения корректного HTML-рендеринга и предотвращения XSS уязвимостей.
| Ввод | Вывод |
|---|---|
& | & |
< | & |
> | & |
" | & |
' | & |
Например, результат <b>Bold< будет санитизирован в <b>Bold<.
Вы можете изменить это поведение, указав text при создании экземпляра Entities:
- Если вы не укажете
text, по умолчанию будет использоватьсяSanitizer sanitizerдля санитизации.Html - Установка значения в
falseотключит санитизацию, сохраняя текст вывода в исходном виде. Это не рекомендуется, так как может привести к некорректному рендерингу и сделать ваше приложение уязвимым для XSS атак. Если вы выбираете этот вариант, убедитесь в правильной обработке данных. - Если вы предоставите функцию, она будет использована вместо стандартного санитайзера.
const myTextSanitizer: TextSanitizer = (options: TextSanitizerOption): string =>
// Замените опасные символы
options.text.replaceAll(/[&<>"']/, (match) => {
switch (match) {
case "&":
return "&";
case "<":
return "<";
case ">":
return ">";
case '"':
return """;
case "'":
return "'";
default:
return match;
}
});
// Используйте собственный санитайзер
const entitiesParser = new EntitiesParser({ textSanitizer: myTextSanitizer });2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
Случаи, когда лучше не использовать этот пакет
Если вы сталкиваетесь с проблемами, подобными перечисленным ниже, возможно, вы сможете решить их без использования этого пакета.
Копирование и пересылка одного и того же сообщения
Используйте метод forward для пересылки сообщений любого типа.
Вы также можете воспользоваться методом copy, который выполняет ту же задачу, но без ссылки на оригинальное сообщение. Метод copy работает как копирование сообщения и отправка его обратно в Telegram, что делает его похожим на обычное сообщение, а не на пересланное.
bot.on(":text", async (ctx) => {
// ID целевого чата для отправки.
const chatId = -946659600;
// Копировать текущее сообщение без ссылки на оригинальное.
await ctx.copyMessage(chatId);
// Переслать текущее сообщение с ссылкой на оригинальное.
await ctx.forwardMessage(chatId);
});2
3
4
5
6
7
8
Ответ на сообщения с изменённым форматом текста
Вы можете легко отвечать на входящие сообщения, используя HTML, Markdown или сущности.
bot.on(":text", async (ctx) => {
// Ответ с использованием HTML
await ctx.reply("<b>жирный</b> <i>курсив</i>", { parse_mode: "HTML" });
// Ответ с использованием Telegram Markdown V2
await ctx.reply("*жирный* _курсив_", { parse_mode: "MarkdownV2" });
// Ответ с использованием сущностей
await ctx.reply("жирный курсив", {
entities: [
{ offset: 0, length: 6, type: "bold" },
{ offset: 7, length: 6, type: "italic" },
],
});
});2
3
4
5
6
7
8
9
10
11
12
13
Используйте parse-mode для улучшенного форматирования
Используйте официальный плагин parse для более удобного создания форматированных сообщений.