Movatterモバイル変換


[0]ホーム

URL:


Skip to content

Navigation Menu

Sign in
Appearance settings

Search code, repositories, users, issues, pull requests...

Provide feedback

We read every piece of feedback, and take your input very seriously.

Saved searches

Use saved searches to filter your results more quickly

Sign up
Appearance settings
Poolitzer edited this pageJan 6, 2024 ·45 revisions

Introduction

Ourexamples usually start the bot usingApplication.run_polling. This method uses thegetUpdates API method to receive new updates for your bot. This is fine for smaller to medium-sized bots and for testing, but if your bot receives a lot of traffic, it might slow down the response times. There might be other reasons for you to switch to a webhook-based method for update retrieval.

First things first: You should have a good reason to switch from polling to a webhook. Don't do it simply because it sounds cool.

Polling vs. Webhook

The general difference between polling and a webhook is:

  • Polling (viaget_updates) periodically connects to Telegram's servers to check for new updates
  • A Webhook is a URL you transmit to Telegram once. Whenever a new update for your bot arrives, Telegram sends that update to the specified URL.

Let's explain this with a metaphor.Imagine you want to check if you have mail.

With (long) polling, you have a post office box and need to check yourself if you have new mail.So you rush to the post office and wait in front of your box all day to see if the postman puts something in there - you only go home for small pee breaks.

With a webhook, you have a mailbox right at your home and the postman delivers the mail right to that mailbox. However, that only works if the postman knows your address (the URL).

Requirements

A public IP address or domain

Usually this means you have to run your bot on a server, either a dedicated server or a VPS. ReadWhere to host Telegram Bots to find a list of options.

Make sure you can connect to your server from thepublic internet, either by IP or domain name. Ifping works, you're good to go.

A SSL certificate

All communication with the Telegram servers must be encrypted with HTTPS using SSL. With polling, this is taken care of by the Telegram Servers, but if you want to receive updates via a Webhook, you have to take care of it. Telegram will not send you any updates if you don't.

There are two ways to do this:

  1. A verified certificate issued by a trusted certification authority (CA)
  2. A self-signed certificate

If you don't already have a verified certificate, use a self-signed one. It's easier and there is no disadvantage to it.

Creating a self-signed certificate using OpenSSL

To create a self-signed SSL certificate usingopenssl, run the following command:

openssl req -newkey rsa:2048 -sha256 -noenc -keyout private.key -x509 -days 3650 -out cert.pem

Theopenssl utility will ask you for a few details.Make sure you enter the correct FQDN! If your server has a domain, enter the full domain name here (eg.sub.example.com). If your server only has an IP address, enter that instead. If you enter an invalid FQDN (Fully Qualified Domain Name), you won't receive any updates from Telegram but also won't see any errors!

Choosing a server model

There actually is a third requirement: a HTTP server to listen for webhook connections. At this point, there are several things to consider, depending on your needs.

The integrated webhook server

Thepython-telegram-bot library ships a custom HTTP server that is tightly integrated in thetelegram.ext module and can be started usingUpdater.start_webhook/Application.run_webhook. This webserver also takes care of decrypting the HTTPS traffic. It is probably the easiest way to set up a webhook.

However, there is a limitation to this solution. Telegram currently only supports four ports for webhooks:443, 80, 88 and8443. As a result, you can only runa maximum of four bots on one domain/IP address with the integrated server.

If that's not a problem for you (yet), you can use the code below (or similar) to start your bot with a webhook. Thelisten address should either be'0.0.0.0' or, if you don't have permission for that, the public IP address of your server. The port can be one of443,80,88 or8443. It is recommended to set a secret token in thesecret_token parameter, so no one can send fake updates to your bot.key andcert should contain the path to the files you generatedearlier. Thewebhook_url should be the actual URL of your webhook. Include thehttps:// protocol in the beginning, use the domain or IP address you set as the FQDN of your certificate and the correct port and URL path.

application.run_webhook(listen='0.0.0.0',port=8443,secret_token='ASecretTokenIHaveChangedByNow',key='private.key',cert='cert.pem',webhook_url='https://example.com:8443')

Remember to observethe limitations for the secret token, otherwise Telegram will not accept it.

It obviously not such a good idea to store the value ofsecret_token right in your code, so consider creating an environment variable for it.

Reverse proxy + integrated webhook server

To overcome the port limitation, you can use a reverse proxy likenginx orhaproxy.

In this model, a single server application listening on the public IP, thereverse proxy, accepts all webhook requests and forwards them to the correct instance of locally runningintegrated webhook servers. It also performs theSSL termination, meaning it decrypts the HTTPS connection, so the webhook servers receive the already decrypted traffic. These servers can run onany port, not just the four ports allowed by Telegram, because Telegram only connects to the reverse proxy directly.

Depending on the reverse proxy application you (or your hosting provider) are using, the implementation will look a bit different. In the following, there are a few possible setups listed.

Heroku

On Heroku using webhook can be beneficial because it will automatically manage the downtime required.The reverse proxy is set up for you and an environment is created. From this environment you will have to extract the port the bot is supposed to listen on. Heroku manages the SSL on the proxy side, so you don't have to provide the certificate yourself.

importosTOKEN="TOKEN"PORT=int(os.environ.get('PORT','8443'))# add handlersapplication.run_webhook(listen="0.0.0.0",port=PORT,secret_token='ASecretTokenIHaveChangedByNow',webhook_url="https://<appname>.herokuapp.com/")

Using nginx with one domain/port for all bots

This is similar to the Heroku approach, just that you set up the reverse proxy yourself. All bots set theirurl to the same domain and port. To differentiate the bots, add a differenturl_path. The integrated server should usually be started on thelocalhost or127.0.0.1 address, the port can be any port you choose.

Note:example.com could be replaced by an IP address if you have no domain associated to your server.

Example code to start the bot:

application.run_webhook(listen='127.0.0.1',port=5000,url_path='1',secret_token='ASecretTokenIHaveChangedByNow',webhook_url='https://example.com/1',cert='cert.pem')

When setting up nginx, it is usually a good idea to secure it with an SSL certificate right away (see for examplethis tutorial). If you've done that, you must not pass your certificate incert parameter (if you do, Telegram will return an error).

Example configuration fornginx (reduced to important parts) with two bots configured:

server {    listen              443 ssl;    server_name         example.com;    ssl_certificate     cert.pem;    ssl_certificate_key private.key;    location /TOKEN1 {        proxy_pass http://127.0.0.1:5000/1/;    }    location /TOKEN2 {        proxy_pass http://127.0.0.1:5001/2/;    }}

If you try and reproduce thecustom webhook example while using nginx as a reverse proxy, make sure you remove trailing slashes from the addresses inproxy_pass directive. A trailing slashmay cause status code 307 being emitted by Starlette that is used in the example.

Using haproxy with one subdomain per bot

In this approach, each bot is assigned their ownsubdomain. If your server has the domainexample.com, you could have the subdomainsbot1.example.com,bot2.example.com etc. You will need one certificate for each bot, with the FQDN set for their respective subdomain (or a wildcard certificate). The reverse proxy in this example ishaproxy. The integrated server should usually be started on thelocalhost or127.0.0.1 address, the port can be any port you choose.

Note: For this to work, you need a domain for your server.

Example code to start the bot:

application.run_webhook(listen='127.0.0.1',port=5000,secret_token='ASecretTokenIHaveChangedByNow',webhook_url='https://bot1.example.com',cert='cert_bot1.pem'))

Example configuration forhaproxy (reduced to important parts) with two bots configured. Again: The FQDN of both certificates must match the value inssl_fc_sni. Also, the.pem files are theprivate.key file andcert.pem files concatenated:

frontend  public-https    bind        0.0.0.0:443 ssl crt cert_key_bot1.pem crt cert_key_bot2.pem    option      httpclose    use_backend bot1 if  { ssl_fc_sni bot1.example.com }    use_backend bot2 if  { ssl_fc_sni bot2.example.com }backend bot1    mode            http    option          redispatch    server          bot1.example.com 127.0.0.1:5000 check inter 1000backend bot2    mode            http    option          redispatch    server          bot2.example.com 127.0.0.1:5001 check inter 1000

Custom solution

You don't necessarily have to use the integrated webserverat all. If you choose to go this way,you should not use theUpdater class. Thetelegram.ext module was designed with this option in mind, so you can still use theApplication class to profit from the message filtering/sorting it provides. You will have to do some work by hand, though.

The general idea is outlined below and also explained in more detail inthis wiki section.

fromtelegramimportBotfromtelegram.extimportApplicationapplication=Application.builder().token('TOKEN').build()# Register handlers here# Get the update_queue from which the application fetches the updates to handleupdate_queue=application.update_queuestart_fetching_updates(update_queue)# Start and run the applicationasyncwithapplication:application.start()# when some shutdown mechanism is triggered:application.stop()

Here,start_fetching_updates is a placeholder for whichever method you use to set up a webhook.The important part is that you enqueue the received updates into theupdate_queue.That is, callawait update_queue.put(update), whereupdate is the decodedUpdate object (useUpdate.de_json(json.loads(text), bot) to decode the update from the received JSON data).

We have an example using this approach availablehere.

Alternative: No long running tasks

If you don't want to use the long running tasks started byapplication.start(), you don't have to!Instead of putting the updates into theupdate_queue, you can directly process them viaapplication.process_update(update).

Checking your webhook

To check if the webhook was accepted by Telegram, you can simply open this link in your browser:https://api.telegram.org/bot<your_bot_token>/getWebhookInfo

Wiki ofpython-telegram-bot © Copyright 2015-2025 – Licensed byCreative Commons

Must read

  1. Introduction to the API
  2. Tutorial: Your first bot
  3. FAQ
  4. How to ask good questions
  5. How to write an MWE

Concepts & Important Elements

  1. Architecture Overview
  2. Builder Pattern forApplication
  3. Types of Handlers
  4. Working with Files and Media
  5. Exceptions, Warnings and Logging
  6. Concurrency in PTB

Notable Features

  1. Advanced Filters
  2. Storing data
  3. Making your bot persistent
  4. Adding Defaults
  5. Job Queue
  6. Arbitrarycallback_data
  7. Avoiding flood limits
  8. Webhooks
  9. Bot API Forward Compatiblity

Code Resources

  1. Frequently requested design patterns
  2. Code snippets
  3. Performance Optimizations
  4. Telegram Passport
  5. Bots built with PTB
  6. Automated Bot Tests

Examples explained

  1. InlineKeyboard Example

Networking

  1. Working Behind a Proxy
  2. Handling network errors

Other resources

  1. Where to host Telegram Bots
  2. How to host your bot
  3. Local API Server
  4. Type Checking with PTB
  5. Press
  6. Notes on GAE
  7. Related Projects
  8. Emoji

Transition Guides

Administration

Clone this wiki locally

[8]ページ先頭

©2009-2025 Movatter.jp