Welcome to python-telegram’s documentation¶
Tutorial¶
How to build a simple echo-bot with python-telegram
¶
Install the library:
python3 -m pip install python-telegram
Let’s create a simple echo-bot, which sends “pong” when it receives “ping”.
Initialize a new telegram client with your credentials:
from telegram.client import Telegram
tg = Telegram(
api_id=123456,
api_hash='api_hash',
phone='+31611111111',
database_encryption_key='changeme1234',
)
Note
The library (actually tdlib
) stores messages database and received files in the /tmp/.tdlib_files/{phone_number}/
.
You can change this behaviour with the files_directory
parameter.
Note
You can use bot tokens: just pass bot_token
instead of phone
.
After that, you have to login:
tg.login()
In this example we use a blocking version of the login function. You can find an example for non-blocking usage here: Non blocking login. Telegram will send you a code in an SMS or as a Telegram message. If you have enabled 2FA, you will be asked for your password too. After successful login you can start using the library:
# this function will be called
# for each received message
def new_message_handler(update):
print('New message!')
tg.add_message_handler(new_message_handler)
tg.idle() # blocking waiting for CTRL+C
This code adds a new message handler which prints a simple text every time it receives a new message.
tg.idle()
is neccessary to block your script and wait for an exit shortcut (CTRL+C
).
If you run this code, you will see something like that:
New message!
New message!
Let’s add more logic to the message handler:
def new_message_handler(update):
# we want to process only text messages
message_content = update['message']['content'].get('text', {})
message_text = message_content.get('text', '').lower()
is_outgoing = update['message']['is_outgoing']
if not is_outgoing and message_text == 'ping':
chat_id = update['message']['chat_id']
print(f'Ping has been received from {chat_id}')
tg.send_message(
chat_id=chat_id,
text='pong',
)
Full code of our new bot:
from telegram.client import Telegram
tg = Telegram(
api_id=123456,
api_hash='api_hash',
phone='+31611111111',
database_encryption_key='changeme1234',
)
tg.login()
def new_message_handler(update):
# we want to process only text messages
message_content = update['message']['content'].get('text', {})
message_text = message_content.get('text', '').lower()
is_outgoing = update['message']['is_outgoing']
if not is_outgoing and message_text == 'ping':
chat_id = update['message']['chat_id']
print(f'Ping has been received from {chat_id}')
tg.send_message(
chat_id=chat_id,
text='pong',
)
tg.add_message_handler(new_message_handler)
tg.idle()
Done! You have created your first client for the Telegram Messenger.
idle and stop¶
You must call stop to properly stop python-telegram and tdlib. It calls tdlib’s close method and waits until it’s finished.
When you use idle, it automatically waits until you call stop in another thread, or one of the stop signals is received.
Non blocking login¶
By default python-telegram uses blocking login method. It presents a prompt to the user for password and code. It makes it hard to use python-telegram as a web app. In this case you might want non blocking login.
telegram.client.Telegram
instance keeps current authoriaztion state in authorization_state
property. You can also request it from tdlib by calling get_authorization_state()
method.
login(blocking=False)
tries to login, but when Telegram needs a password or a code, it returns current authorization state and gives you ability to provide it manually.
When the code is sent (using send_code
method), you can call login(bloking=False)
again to continue the process. When the user logged it, login returns AuthorizationState.READY
.
Let’s have a look at the example.
- Initialize the client:
from telegram.client import Telegram, AuthorizationState
tg = Telegram(
api_id='api_id',
api_hash='api_hash',
phone='+31611111111',
database_encryption_key='changeme1234',
)
- Call
tg.login(blocking=False)
. It returns a newAuthorizationState
:
code = 'some-code'
password = 'secret-password'
state = tg.login(blocking=False)
if state == AuthorizationState.WAIT_CODE:
# Telegram expects a pin code
tg.send_code(code)
state = tg.login(blocking=False) # continue the login process
if state == AuthorizationState.WAIT_PASSWORD:
tg.send_password(password)
state = tg.login(blocking=False) # continue the login process
# Logged in.
# You can also check that tg.authorization state is AuthorizationState.READY.
We analyze the authorization state, send code or password and continue the login process after.
Currently you can expect only two blocking authorization states: AuthorizationState.WAIT_CODE
and AuthorizationState.WAIT_PASSWORD
.
You can find the full example in the repository, examples/get_me_non_blocking_login.py
.
telegram package¶
Submodules¶
telegram.client module¶
telegram.tdjson module¶
telegram.utils module¶
-
class
telegram.utils.
AsyncResult
(client: Telegram, result_id: Optional[str] = None)¶ Bases:
object
tdlib is asynchronous, and this class helps you get results back. After each API call, you receive AsyncResult object, which you can use to get results back.
-
parse_update
(update: Dict[Any, Any]) → bool¶
-
wait
(timeout: Optional[int] = None, raise_exc: bool = False) → None¶ Blocking method to wait for the result
-
telegram.worker module¶
-
class
telegram.worker.
BaseWorker
(queue: queue.Queue)¶ Bases:
object
Base worker class. Each worker must implement the run method to start listening to the queue and calling handler functions
-
run
() → None¶
-
stop
() → None¶
-
-
class
telegram.worker.
SimpleWorker
(queue: queue.Queue)¶ Bases:
telegram.worker.BaseWorker
Simple one-thread worker
-
run
() → None¶
-
stop
() → None¶
-
Module contents¶
tdlib¶
How to build tdlib¶
Do not forget install the library after:
make install
- Also, you can use it with Docker:
- tdlib only tdlib-docker
- this package + tdlib python-telegram-docker
You can call any method of tdlib
with python-telegram
using call_method
:
tg = Telegram(...)
params = {'user_id': 1}
result = tg.call_method('getUser', params)
Proxy¶
How to use a proxy with tdlib¶
Define proxy parameters and pass them to Telegram
:
from telegram.client import Telegram
proxy_type = {
'@type': 'proxyTypeMtproto', # 'proxyTypeSocks5', 'proxyTypeHttp'
}
proxy_port = 1234
proxy_server = 'localhost'
tg = Telegram(
api_id='api_id',
api_hash='api_hash',
phone='+31611111111',
database_encryption_key='changeme1234',
proxy_server=proxy_server,
proxy_port=proxy_port,
proxy_type=proxy_type,
)
Changelog¶
[unreleased]
- Python 3.7 is no longer supported.
[0.18.0] - 2023-03-13
- Added support for tdlib > 1.8.5. (thanks to @JleMyP)
[0.17.0] - 2023-01-25
- Added
import_contacts
method. (thanks to @vlad-lf) - Added markup support. It is now possible to send formatted text (html/markdown and telegram-specific formats, for example hidden spoiler styling) (thanks to @SKY-ALIN)
[0.16.0] - 2022-08-18
- Search for the system library first, and fallback to the embedded one if the system was not found.
- Fixed the finding system library mechanism (thanks to @weirdo-neutrino)
- tdlib v1.8.5
[0.15.0] - 2021-12-03
- tdlib v1.7.9. Fixes
UPDATE_APP_TO_LOGIN
errors.
[0.14.0] - 2020-12-17
- tdlib v1.7.0
[0.13.0] - 2020-11-16
- Non-blocking login, see
examples/get_me_non_blocking_login.py
(thanks to @melfnt). - Better stop. python-teleram calls close and waits until tdlib is closed.
[0.12.0] - 2020-03-29
- New example:
examples/clear_group_messages.py
(thanks to @h4x3rotab) - Proxy support (thanks to @h4x3rotab)
- New methods:
delete_messages
,get_supergroup_full_info
,create_basic_group_chat
. (thanks to @h4x3rotab) - Fix #67: fixed infinite waiting for a result during login or for an ok result type.
- New Telegram initialization parameter:
use_secret_chats
(True
by default) (thanks to @DopeforHope) - Fix #81:
encryption_key
for tdlib database encryption is now being sent to tdlib as a base64 encoded string.
[0.11.0] - 2020-02-15
tdlib
upgraded tov1.6.0
(from this repository)- Added a new parameter to the
call_method
:block=False
. If it is set toTrue
, the method waits for the result from tdlib. - Added
Telegram.get_message
method (thanks to @ali-shokoohi) - Fixed a race condition when in some cases
AsyncResult.wait()
could raiseTimeoutError
or end up in an endless loop. (thanks to @akamaus) - Added a new method:
get_user
. - Added
Telegram.remove_update_handler
function to remove update handlers.
[0.10.0] - 2019-04-10
- Incompatible Linux library has been changed, now it’s compiled on Ubuntu with libc.
[0.9.0] - 2019-04-05
- Incompatible default path for files is changed. Now the library uses an md5 hash of the phone number or bot token instead of just a phone number.
It should not be noticeable for most cases, but if you rely on locally saved files or database, you need to pass the
files_directory
parameter to thetelegram.client.Telegram
. - Fixed problem with randomly raised “Database encryption key is needed” errors during login process. (#12)
- Fixed
stop
method execution. (#8) - Added
examples/bot_login.py
example.
[0.8.0] - 2019-03-17
telegram.client.Telegram
now supports any update type with a new methodadd_update_handler(handler_type, func)
tdlib v 1.3.0
- Fixed problem with openssl in Dockerfile (#4)
[0.7.0]
- New method
getMe
with an example.
[0.6.1] - 2018-05-01
- Fixes for the Linux pre-compiled tdlib library.
[0.6.0] - 2018-05-01
- Fixes for the Linux pre-compiled tdlib library.
[0.5.0] - 2018-05-01¶
New required parameter in the
telegram.client.Telegram
:database_encryption_key
.Compiled
tdlib
files now are in the pypi package (Linux and MacOS).Default location of the tdlib’s files changed to
/tmp/.tdlib_files/{phone_number}
.Now you can define additional optional params:
- use_test_dc (default False)
- device_model
- system_version
- system_language_code
- application_version
- use_message_database (default True)
Added new example: chat_stats.py.
[0.4.0] - 2018-04-29¶
Added two new methods:
get_instant_view
- get instant view of a web pagecall_method
- call any method with any params
New example: get_instant_view.py
[0.3.1] - 2018-04-29¶
- Logging level in the examples changed to
INFO
. - Added new
Makefile
command:docker-echo-bot
. - All
docker-
commands in theMakefile
now mount/tmp/
from a host machine to store tdlib’s files.
[0.3.0] - 2018-04-28¶
- Added
Dockerfile
andMakefile
with some examples. - Changed directory for tdlib files to
/tmp/.tdlib_files_{self.phone}/
.
Client for the tdlib library (at very early stage :) ).
Installation¶
At first you must install tdlib
.
Library installation¶
This library works with Python 3.8+ only.
python3 -m pip install python-telegram
After you must register a new Telegram application.
Now you can start using the library: Tutorial.
Note
You can find more examples here.
Note
The tdlib
binary for Linux provided by python-shortcuts
is built on Ubuntu with libc since version 0.10.0
. Before 0.10.0
, Alpine Linux was used with musl
.
Docker¶
This library has a docker image
docker run -i -t --rm \
-v /tmp/docker-python-telegram/:/tmp/ \
akhmetov/python-telegram \
python3 /app/examples/send_message.py $(API_ID) $(API_HASH) $(PHONE) $(CHAT_ID) $(TEXT)