1
0
mirror of https://github.com/eternnoir/pyTelegramBotAPI.git synced 2023-08-10 21:12:57 +03:00

Merge pull request #195 from aivel/master

Some changes to make the library more flexible in terms of extensibility
This commit is contained in:
FrankWang 2016-06-13 22:33:42 +08:00 committed by GitHub
commit c7d2731559

View File

@ -174,7 +174,7 @@ class TeleBot:
def __notify_update(self, new_messages): def __notify_update(self, new_messages):
for listener in self.update_listener: for listener in self.update_listener:
self.__exec_task(listener, new_messages) self._exec_task(listener, new_messages)
def polling(self, none_stop=False, interval=0, timeout=20): def polling(self, none_stop=False, interval=0, timeout=20):
""" """
@ -260,7 +260,7 @@ class TeleBot:
logger.info('Stopped polling.') logger.info('Stopped polling.')
def __exec_task(self, task, *args, **kwargs): def _exec_task(self, task, *args, **kwargs):
if self.threaded: if self.threaded:
self.worker_pool.put(task, *args, **kwargs) self.worker_pool.put(task, *args, **kwargs)
else: else:
@ -643,7 +643,7 @@ class TeleBot:
if chat_id in self.message_subscribers_next_step: if chat_id in self.message_subscribers_next_step:
handlers = self.message_subscribers_next_step[chat_id] handlers = self.message_subscribers_next_step[chat_id]
for handler in handlers: for handler in handlers:
self.__exec_task(handler, message) self._exec_task(handler, message)
self.message_subscribers_next_step.pop(chat_id, None) self.message_subscribers_next_step.pop(chat_id, None)
def _append_pre_next_step_handler(self): def _append_pre_next_step_handler(self):
@ -654,7 +654,13 @@ class TeleBot:
self.message_subscribers_next_step[k] = self.pre_message_subscribers_next_step[k] self.message_subscribers_next_step[k] = self.pre_message_subscribers_next_step[k]
self.pre_message_subscribers_next_step = {} self.pre_message_subscribers_next_step = {}
def message_handler(self, commands=None, regexp=None, func=None, content_types=['text']): def _build_handler_dict(self, handler, **filters):
return {
'function': handler,
'filters': filters
}
def message_handler(self, commands=None, regexp=None, func=None, content_types=['text'], **kwargs):
""" """
Message handler decorator. Message handler decorator.
This decorator can be used to decorate functions that must handle certain types of messages. This decorator can be used to decorate functions that must handle certain types of messages.
@ -685,130 +691,95 @@ class TeleBot:
""" """
def decorator(handler): def decorator(handler):
self.add_message_handler(handler, commands, regexp, func, content_types) handler_dict = self._build_handler_dict(handler,
commands=commands,
regexp=regexp,
func=func,
content_types=content_types,
**kwargs)
self.add_message_handler(handler_dict)
return handler return handler
return decorator return decorator
def add_message_handler(self, handler, commands=None, regexp=None, func=None, content_types=None): def add_message_handler(self, handler_dict):
if content_types is None:
content_types = ['text']
filters = {'content_types': content_types}
if regexp:
filters['regexp'] = regexp
if func:
filters['lambda'] = func
if commands:
filters['commands'] = commands
handler_dict = {
'function': handler,
'filters': filters
}
self.message_handlers.append(handler_dict) self.message_handlers.append(handler_dict)
def edited_message_handler(self, commands=None, regexp=None, func=None, content_types=['text']): def edited_message_handler(self, commands=None, regexp=None, func=None, content_types=['text'], **kwargs):
def decorator(handler): def decorator(handler):
self.add_edited_message_handler(handler, commands, regexp, func, content_types) handler_dict = self._build_handler_dict(handler,
commands=commands,
regexp=regexp,
func=func,
content_types=content_types,
**kwargs)
self.add_edited_message_handler(handler_dict)
return handler return handler
return decorator return decorator
def add_edited_message_handler(self, handler, commands=None, regexp=None, func=None, content_types=None): def add_edited_message_handler(self, handler_dict):
if content_types is None:
content_types = ['text']
filters = {'content_types': content_types}
if regexp:
filters['regexp'] = regexp
if func:
filters['lambda'] = func
if commands:
filters['commands'] = commands
handler_dict = {
'function': handler,
'filters': filters
}
self.edited_message_handlers.append(handler_dict) self.edited_message_handlers.append(handler_dict)
def inline_handler(self, func): def inline_handler(self, func):
def decorator(handler): def decorator(handler):
self.add_inline_handler(handler, func) handler_dict = self._build_handler_dict(handler, func=func)
self.add_inline_handler(handler_dict)
return handler return handler
return decorator return decorator
def add_inline_handler(self, handler, func): def add_inline_handler(self, handler_dict):
filters = {'lambda': func}
handler_dict = {
'function': handler,
'filters': filters
}
self.inline_handlers.append(handler_dict) self.inline_handlers.append(handler_dict)
def chosen_inline_handler(self, func): def chosen_inline_handler(self, func):
def decorator(handler): def decorator(handler):
self.add_chosen_inline_handler(handler, func) handler_dict = self._build_handler_dict(handler, func=func)
self.add_chosen_inline_handler(handler_dict)
return handler return handler
return decorator return decorator
def add_chosen_inline_handler(self, handler, func): def add_chosen_inline_handler(self, handler_dict):
filters = {'lambda': func}
handler_dict = {
'function': handler,
'filters': filters
}
self.chosen_inline_handlers.append(handler_dict) self.chosen_inline_handlers.append(handler_dict)
def callback_query_handler(self, func): def callback_query_handler(self, func):
def decorator(handler): def decorator(handler):
self.add_callback_query_handler(handler, func) handler_dict = self._build_handler_dict(handler, func=func)
self.add_callback_query_handler(handler_dict)
return decorator return decorator
def add_callback_query_handler(self, handler, func): def add_callback_query_handler(self, handler_dict):
filters = {'lambda': func}
handler_dict = {
'function': handler,
'filters': filters
}
self.callback_query_handlers.append(handler_dict) self.callback_query_handlers.append(handler_dict)
@staticmethod def _test_message_handler(self, message_handler, message):
def _test_message_handler(message_handler, message):
for filter, filter_value in six.iteritems(message_handler['filters']): for filter, filter_value in six.iteritems(message_handler['filters']):
if not TeleBot._test_filter(filter, filter_value, message): if filter_value is None:
continue
if not self._test_filter(filter, filter_value, message):
return False return False
return True return True
@staticmethod def _test_filter(self, filter, filter_value, message):
def _test_filter(filter, filter_value, message): test_cases = {
if filter == 'content_types': 'content_types': lambda msg: msg.content_type in filter_value,
return message.content_type in filter_value 'regexp': lambda msg: msg.content_type == 'text' and re.search(filter_value, msg.text),
if filter == 'regexp': 'commands': lambda msg: msg.content_type == 'text' and util.extract_command(msg.text) in filter_value,
return message.content_type == 'text' and re.search(filter_value, message.text) 'func': lambda msg: filter_value(msg)
if filter == 'commands': }
return message.content_type == 'text' and util.extract_command(message.text) in filter_value
if filter == 'lambda': return test_cases.get(filter, lambda msg: False)(message)
return filter_value(message)
return False
def _notify_command_handlers(self, handlers, new_messages): def _notify_command_handlers(self, handlers, new_messages):
for message in new_messages: for message in new_messages:
for message_handler in handlers: for message_handler in handlers:
if self._test_message_handler(message_handler, message): if self._test_message_handler(message_handler, message):
self.__exec_task(message_handler['function'], message) self._exec_task(message_handler['function'], message)
break break