Handle multiple questions for Telegram bot in python
Question: I'm programming a telegram bot in Python using the Telegram bot API. I'm
facing the problem of managing questions that need an answer of the user. The
problem arises when the program is waiting for an answer of one user and
another user request information or ask another question **before** the first
user responds.

The Telegram API uses a code to handle the request. When you ask for updates
you include a code. If the code you send is higher than a request code, it is
mark as handled and telegram delete it and no longer appears in the updates.
This code is sequential, so if you mark update 3 as handled, updates 1 and 2
are erased as well.

The question is **why is the best phytonic/elegant way to handle multiple
requests that needs an answer for the users?**


Answer: There is not a most pythonic way of doing this. It is a problem you have to
_program_ to solve.

Basically, you have to maintain some state variables concerning each user.
When a new message arrives, the bot checks what state that user is in, and
responds accordingly.

Suppose you have a function, `handle(msg)`, that gets called for each arriving
message:

    
    
    user_states = {}
    
    def handle(msg):
        chat_id = msg['chat']['id']
    
        if chat_id not in user_states:
            user_states[chat_id] = some initial state ...
    
        state = user_states[chat_id]
    
        # respond according to `state`
    

This will do for a simple program.

For more complicated situations, I recommend using
**[telepot](https://github.com/nickoala/telepot), a Python framework I have
created for Telegram Bot API**. It has features that specifically solve this
kind of problems.

For example, below is a bot that counts how many messages have been sent by an
individual user. If no message is received after 10 seconds, it starts over
(timeout). The counting is done _per chat_ \- that's the important point.

    
    
    import sys
    import telepot
    from telepot.delegate import per_chat_id, create_open
    
    class MessageCounter(telepot.helper.ChatHandler):
        def __init__(self, seed_tuple, timeout):
            super(MessageCounter, self).__init__(seed_tuple, timeout)
            self._count = 0
    
        def on_message(self, msg):
            self._count += 1
            self.sender.sendMessage(self._count)
    
    TOKEN = sys.argv[1]  # get token from command-line
    
    bot = telepot.DelegatorBot(TOKEN, [
        (per_chat_id(), create_open(MessageCounter, timeout=10)),
    ])
    bot.notifyOnMessage(run_forever=True)
    

Run the program by:

    
    
    python messagecounter.py <token>
    

[Go to the project page](https://github.com/nickoala/telepot) to learn more if
you are interested. There are a lot of documentations and non-trivial
examples.

