120 lines
3.6 KiB
Markdown
120 lines
3.6 KiB
Markdown
# Telegram OpenAI-Compatible Bot
|
|
|
|
Minimal aiogram bot that forwards whitelisted Telegram users' text messages to an OpenAI-compatible chat completions API.
|
|
|
|
## Features
|
|
|
|
- Configurable `API_BASE_URL` and `API_TOKEN`
|
|
- Optional proxy for Telegram API and OpenAI-compatible API connections
|
|
- Telegram typing animation while the model response is streaming
|
|
- Required users whitelist
|
|
- Persistent per-user context in SQLite
|
|
- `/new` command to reset the current user's context
|
|
- Per-user message batching before sending to the model
|
|
- Model-controlled multi-message replies with `<break>` tags
|
|
- Configurable model and system prompt
|
|
- API timeouts, retries, response limits, and safe user-facing fallbacks
|
|
- System prompt stored in `config/system_prompt.txt`, not `.env`
|
|
|
|
## Setup
|
|
|
|
1. Install dependencies:
|
|
|
|
```bash
|
|
python -m pip install -r requirements.txt
|
|
```
|
|
|
|
2. Create local environment config:
|
|
|
|
```bash
|
|
cp .env.example .env
|
|
```
|
|
|
|
3. Edit `.env`:
|
|
|
|
```dotenv
|
|
BOT_TOKEN=123456:telegram-token
|
|
API_BASE_URL=https://api.openai.com/v1
|
|
API_TOKEN=sk-your-api-token
|
|
MODEL=gpt-4o-mini
|
|
WHITELIST_USER_IDS=123456789
|
|
DATABASE_PATH=data/bot.sqlite3
|
|
MAX_CONTEXT_MESSAGES=20
|
|
MESSAGE_BATCH_DELAY_SECONDS=3
|
|
```
|
|
|
|
`API_BASE_URL` must be the API root. Do not include `/chat/completions`; the OpenAI SDK appends that path automatically.
|
|
|
|
For OpenRouter, use:
|
|
|
|
```dotenv
|
|
API_BASE_URL=https://openrouter.ai/api/v1
|
|
```
|
|
|
|
4. Edit `config/system_prompt.txt` with the system prompt you want.
|
|
|
|
5. Run the bot:
|
|
|
|
```bash
|
|
python bot.py
|
|
```
|
|
|
|
## Proxy
|
|
|
|
Set `TELEGRAM_PROXY` in `.env` to route both Telegram API and OpenAI-compatible API traffic through a proxy:
|
|
|
|
```dotenv
|
|
TELEGRAM_PROXY=socks5://user:pass@127.0.0.1:1080
|
|
```
|
|
|
|
Leave it empty when no proxy is needed.
|
|
|
|
## Context
|
|
|
|
The bot stores successful user/assistant turns in SQLite at `DATABASE_PATH`. Each Telegram user has separate context, and each new request sends the latest `MAX_CONTEXT_MESSAGES` stored messages plus the new user message.
|
|
|
|
Send `/new` to delete your stored messages and start a fresh conversation.
|
|
|
|
## Message Batching
|
|
|
|
`MESSAGE_BATCH_DELAY_SECONDS` delays the API request after each incoming Telegram message. If the same user sends more messages during that delay, the timer restarts and the messages are sent to the model together as separate entries:
|
|
|
|
```text
|
|
Message 1: first telegram message
|
|
Message 2: second telegram message
|
|
Message 3: third telegram message
|
|
```
|
|
|
|
This keeps stacked messages distinct without merging them into one paragraph. Set `MESSAGE_BATCH_DELAY_SECONDS=1` for faster replies or a higher value if you often send several short messages in a row.
|
|
|
|
## Multi-Message Replies
|
|
|
|
The model can split one response into multiple Telegram messages by emitting break tags:
|
|
|
|
```text
|
|
First message
|
|
<break>
|
|
Second message
|
|
<break timeout=5>
|
|
Third message after 5 seconds
|
|
```
|
|
|
|
Supported tags:
|
|
|
|
- `<break>` sends the next part immediately
|
|
- `<break timeout=5>` waits up to 30 seconds before sending the next part
|
|
|
|
Add this instruction to `config/system_prompt.txt` if you want the model to use it naturally:
|
|
|
|
```text
|
|
When a reply is better split into multiple Telegram messages, insert <break> between messages. Use <break timeout=5> when the next message should be delayed by 5 seconds.
|
|
```
|
|
|
|
## Security Notes
|
|
|
|
- `.env` is ignored by git and should contain tokens only.
|
|
- `WHITELIST_USER_IDS` is required so the bot cannot accidentally run as a public API proxy.
|
|
- The bot logs provider errors server-side and sends generic fallbacks to users.
|
|
- `MAX_PROMPT_CHARS` and `MAX_RESPONSE_CHARS` limit oversized requests and Telegram message failures.
|
|
- `data/` is ignored by git because it contains local conversation history.
|