forked from nique_372/TelegramByLeo
174 lines
No EOL
6.6 KiB
Markdown
174 lines
No EOL
6.6 KiB
Markdown
<p align="center">
| |
<img src="https://img.shields.io/badge/Language-MQL5-1B6CA8?style=flat-square"/>
| |
<img src="https://img.shields.io/badge/Platform-MetaTrader%205-0D1B2A?style=flat-square"/>
| |
<img src="https://img.shields.io/badge/Author-nique__372-C9D6DF?style=flat-square&logoColor=white"/>
| |
<img src="https://img.shields.io/badge/MQL5.com-nique__372-1B6CA8?style=flat-square"/>
| |
<a href="./LICENSE"><img src="https://img.shields.io/badge/License-Nique%26Leo%20NL--ND-red.svg"/></a>
| |
</p>
| |
| |
<p align="center">
| |
A fast, low-level Telegram Bot API library for MQL5.<br/> Requests are built directly into raw byte buffers (fixed-offset literal tables + <code>ArrayCopy</code>, a custom <code>CJsonBuilder</code>, and multipart with boundary reuse) instead of going through an intermediate DOM — no per-field allocation, no generic serialization pass.
| |
</p>
| |
| |
---
| |
| |
## Main Features
| |
| |
- **Full Bot API surface** (`CTelegramAPI`): messages, polls (regular/quiz), documents/video/audio/voice/animation/photo (multipart), rich messages, chat actions, reactions, member management (ban/unban/restrict/promote), bot profile, chat management, callback query answers, message/reply-markup editing, poll stopping, deletes.
| |
- **Independent long-polling updater** (`CTelegramBotUpdater` + `CTelegramHandler`): decoupled from `CTelegramAPI` — the bot only calls the API, the updater only polls and dispatches. Handlers register per event (27 event types) via bitmask or one at a time; `AllowedUpdates()` can auto-compute the `allowed_updates` filter from whichever events actually have a handler registered, so you don't get updates nobody is listening for.
| |
- **Perfect-hash update dispatch**: incoming `getUpdates` keys are matched via a generated perfect hash (`EnumReg`), not string comparisons, before landing in the event `switch`.
| |
- **Keyboard builders** (`CTlgInlineKeyboard`, `CTlgReplyKeyboard`): chainable, raw-buffer builders for `InlineKeyboardMarkup` / `ReplyKeyboardMarkup`. Both share a `CTlgKeyboardBase` (buffer + row/button bookkeeping) to avoid duplicating the same comma/bracket logic twice — not an "is-a" hierarchy, just shared plumbing.
| |
- **Snapshot/rollback for speculative writes**: `JsonBuilderSnapshot` (JSON builder) and `TlgKeyboardSnapshot` (keyboards) capture position + internal stack state so an optional nested object (e.g. `reply_parameters`) can be written speculatively and rolled back cleanly if it ends up empty, without corrupting the builder's structural state.
| |
- **Validated vs. trusted string writes**: library-controlled constants (parse mode names, chat actions, field keys) go through the unvalidated/raw path (`KeyWV`/`ValUWV`/`SetBuffer`); arbitrary user input always goes through the escaping path (`ValS`/`SetStr`) — chosen per call site, never blanket-escaped or blanket-trusted.
| |
| |
### Send a message
| |
| |
```mql5
| |
#include "Src\\MainAPI.mqh"
| |
| |
TSN::CTelegramAPI bot;
| |
bot.Token("123456:ABC-your-bot-token");
| |
bot.ChatId(-100123456789);
| |
bot.SendMessage("Hello from MQL5", TSN::TELEGRAM_PARSE_MODE_HTML);
| |
```
| |
| |
### Long polling with handlers
| |
| |
```mql5
| |
#include "Src\\Events.mqh"
| |
| |
class CMyHandler : public TSN::CTelegramHandler
| |
{
| |
public:
| |
void OnMessage(TSN::CJsonNode& node) override
| |
{
| |
Print("Got message: ", node["text"].ToString());
| |
}
| |
};
| |
| |
TSN::CTelegramBotUpdater updater;
| |
CMyHandler handler;
| |
| |
void OnInit()
| |
{
| |
updater.Token("123456:ABC-your-bot-token");
| |
updater.RegisterEvents(&handler, TSN::TELEGRAMBYLEO_REG_FLAG_ON_MESSAGE);
| |
// 20 seconds timeout telegram long polling
| |
updater.Timeout(30000); // 30 seg for web req
| |
updater.Init(20); // getUpdates() body: {"offset":-1,"limit":1}, discards backlog
| |
updater.AllowedUpdates(); // zero parameters (Auto)
| |
}
| |
| |
void OnTimer()
| |
{
| |
updater.GetUpdates();
| |
}
| |
```
| |
| |
### Inline keyboard
| |
| |
```mql5
| |
#include "Src\\Bottons\\Inline.mqh"
| |
| |
TSN::CTlgInlineKeyboard kb;
| |
kb.Init();
| |
kb.AddRow().AddBtnCallbackData("Yes", "vote_yes").AddBtnCallbackData("No", "vote_no").EndRow();
| |
kb.Finish(); // {"inline_keyboard":[[{"text":"Yes","callback_data":"vote_yes"},{"text":"No","callback_data":"vote_no"}]]}
| |
| |
uchar reply_markup[];
| |
bot.SendMessage("Vote:", WRONG_VALUE, base, rp, ep, kb.m_buf, kb.m_pos);
| |
```
| |
| |
### Reply keyboard
| |
| |
```mql5
| |
#include "Src\\Bottons\\ReplyMarkup.mqh"
| |
| |
TSN::CTlgReplyKeyboard kb;
| |
kb.Init();
| |
kb.IsPersistent(false).ResizeKeyboard(true).OneTimeKeyboard(true);
| |
kb.InitArr();
| |
kb.AddRow().AddBtn("Option A").AddBtn("Option B").EndRow();
| |
kb.Finish(); // {"resize_keyboard":true,"one_time_keyboard":true,"keyboard":[["Option A","Option B"]]}
| |
```
| |
| |
---
| |
| |
## Repository Structure
| |
| |
```
| |
TelegramByLeo/
| |
├── Bots/ # Example EAs using the library
| |
├── EnumReg/ # Perfect-hash generator config for update-key dispatch
| |
└── Src/
| |
├── Base/ # Endpoints, shared structs, error/parse-mode enums
| |
├── Bottons/ # Inline/Reply keyboard builders + shared keyboard base
| |
├── Emojis/ # Emoji constant table
| |
└── Old/ # Previous (pre-rewrite) implementation, kept for reference
| |
```
| |
| |
---
| |
| |
## Requirements
| |
| |
See [dependencies.json](./dependencies.json) for the full list.
| |
| |
- MetaTrader 5, build 5430+
| |
- [`WebUtilsByLeo`](https://forge.mql5.io/nique_372/WebUtilsByLeo) — currently a private dependency; contact [@nique_372](https://www.mql5.com/es/users/nique_372) for access.
| |
- `WebRequest` access enabled for `https://api.telegram.org`
| |
| |
---
| |
| |
## Installation
| |
| |
```bash
| |
cd "C:\Users\YOUR_USER\AppData\Roaming\MetaQuotes\Terminal\YOUR_ID\MQL5\Shared Projects"
| |
tsndep install "https://forge.mql5.io/nique_372/TelegramByLeo.git"
| |
```
| |
| |
Requires the `tsndep` package, available on [PyPI](https://pypi.org/project/tsndep). It automatically downloads and installs all declared dependencies.
| |
| |
---
| |
| |
## Quick Start
| |
| |
**1. Include the library:**
| |
| |
```mql5
| |
#include "..\\TelegramByLeo\\Src\\MainAPI.mqh"
| |
```
| |
| |
**2. Set the token and chat, and send something:**
| |
| |
```mql5
| |
TSN::CTelegramAPI bot;
| |
bot.Token("123456:ABC-your-bot-token");
| |
bot.ChatId(-100123456789);
| |
bot.SendMessage("Hello from MQL5");
| |
```
| |
| |
**3. (Optional) Add polling:** see [Long polling with handlers](#long-polling-with-handlers) above.
| |
| |
---
| |
| |
## License
| |
| |
**[Read Full License](./LICENSE)**
| |
By downloading or using this repository, you accept the license terms.
| |
| |
---
| |
| |
## Contact
| |
| |
- **Platform:** [MQL5 Community](https://www.mql5.com/es/users/nique_372)
| |
- **Profile:** https://www.mql5.com/es/users/nique_372
| |
- **Articles:** https://www.mql5.com/es/users/nique_372/publications
| |
| |
---
| |
| |
## Roadmap
| |
| |
- Finish `Get*` methods (`GetMyName`, `GetMyDescription`, `GetMyShortDescription`) using the JSON parser side [In progress]
| |
- `RestrictChatMember` / `PromoteChatMember` bodies
| |
- `KeyboardButtonRequestUsers` / `RequestChat` support in `CTlgReplyKeyboard`
| |
|