def setUp(self): os.environ.setdefault("URL_HOSTNAME", "example.com") app = Flask(__name__) app.config.from_pyfile("testconfig.py") self.app = app self.app_test = app.test_client() # get a test client self.bot = Teleflask(API_KEY, return_python_objects=True) # replace the :class:`pytgbot.Bot` instance with something testable. (not using TG server) # All methods now return the stuff they would sent to the telegram servers as json instead. # This is not usable with the :class:`teleflask.message.Message` (sub)types. self.bot.bot = BotTestable( API_KEY, return_python_objects=self.bot._return_python_objects) # Init must be before replacing the ``bot.bot``, # because else the :meth:`Bot.getWebhook` won't work as expected in startup. self.bot.init_app(app) # Array to hold information about the called callbacks: self.callbacks_status = {} # Get the update_path to be able to test via emulating incoming updates self.update_path, self.update_url = self.bot.calculate_webhook_url( hostname=self.bot.hostname, hostpath=self.bot.hostpath, hookpath=self.bot.hookpath)
def test_doubleblueprintability_and_execute(self): states_tbp = TBlueprint(__name__) states_tbp2 = TBlueprint(__name__ + "2") states_tbp.register_tblueprint(states_tbp2) states_drvr = SilentDriver() states = TeleStateMachine(__name__, database_driver=states_drvr, teleflask_or_tblueprint=states_tbp2) states.teleflask._bot = BotMock('FAKE_API_KEY', return_python_objects=True) called = [False] @states.DEFAULT.command('cancel') def func_1(update, text): called[0] = True # end def bot = Teleflask('FAKE_API_KEY', app=None, hostname="localhost", debug_routes=False, disable_setting_webhook_telegram=True, disable_setting_webhook_route=True) bot._bot = BotMock('FAKE_API_KEY', return_python_objects=True) bot.init_bot() bot.register_tblueprint(states_tbp) bot.process_update(update1) self.assertTrue(called[0], 'func_1 should have been called')
def setUp(self): self.b = Teleflask(api_key=None, app=None, hostname="localhost", debug_routes=False, disable_setting_webhook_telegram=True, disable_setting_webhook_route=True) self.b._bot = BotMock('FAKE_API_KEY', return_python_objects=True) self.d = SilentDriver() self.m = TeleStateMachine(__name__, self.d, self.b) self.s = TeleState('LITTLEPIP') self.b.init_bot()
def test_blueprintability_and_register(self): states_tbp = TBlueprint(__name__) states_drvr = SilentDriver() states: TeleStateMachine = TeleStateMachine( __name__, database_driver=states_drvr, teleflask_or_tblueprint=states_tbp) states.teleflask._bot = BotMock('FAKE_API_KEY', return_python_objects=True) states.teleflask.init_bot() @states.DEFAULT.command('cancel') def func_1(update): pass # end def bot = Teleflask('FAKE_API_KEY', app=None, hostname="localhost", debug_routes=False, disable_setting_webhook_telegram=True, disable_setting_webhook_route=True) bot._bot = BotMock('FAKE_API_KEY', return_python_objects=True) bot.init_bot() bot.register_tblueprint(states_tbp) self.assertGreater(len(states.CURRENT.update_handler.commands), 0, 'should have added an command.')
def __init__(self, name: str, database_driver: Union[Type[TeleStateDatabaseDriver], TeleStateDatabaseDriver], teleflask_or_tblueprint: Teleflask = None): self.did_init = False self.listeners_registered = False self.states: Dict[str, TeleState] = {} # NAME: telestate_instance assert_type_or_raise(database_driver, TeleStateDatabaseDriver, parameter_name='driver') self.database_driver = database_driver super(TeleStateMachine, self).__init__() if teleflask_or_tblueprint: self.blueprint = teleflask_or_tblueprint if isinstance(teleflask_or_tblueprint, Teleflask): # calls register_bot self.register_bot(teleflask_or_tblueprint) # now is registered self.is_registered = True elif isinstance(teleflask_or_tblueprint, TBlueprint): # calls register_bot teleflask_or_tblueprint.record(self.register_bot) # is registered as if that TBlueprint already is registered. self.is_registered = teleflask_or_tblueprint._got_registered_once and teleflask_or_tblueprint._teleflask # end if else: self.blueprint = TBlueprint(name) self.is_registered = False # end def # end if self.active_state = None self.DEFAULT = TeleState('DEFAULT', self) self.ALL = TeleState( 'ALL', self ) # so you can register to states.ALL to be called on all the states. self.CURRENT = self.DEFAULT self.did_init = True
def setUp(self): os.environ.setdefault("URL_HOSTNAME", "example.com") app = Flask(__name__) app.config.from_pyfile("testconfig.py") self.app = app self.app_test = app.test_client() # get a test client self.bot = Teleflask(API_KEY, return_python_objects=True) # replace the :class:`pytgbot.Bot` instance with something testable. (not using TG server) # All methods now return the stuff they would sent to the telegram servers as json instead. # This is not usable with the :class:`teleflask.message.Message` (sub)types. self.bot.bot = BotTestable(API_KEY, return_python_objects=self.bot._return_python_objects) # Init must be before replacing the ``bot.bot``, # because else the :meth:`Bot.getWebhook` won't work as expected in startup. self.bot.init_app(app) # Array to hold information about the called callbacks: self.callbacks_status = {} # Get the update_path to be able to test via emulating incoming updates self.update_path, self.update_url = self.bot.calculate_webhook_url(hostname=self.bot.hostname, hostpath=self.bot.hostpath, hookpath=self.bot.hookpath)
from .utils import to_json_remove_api_key, msg_get_reply_params from .secrets import API_KEY, EVENT_CHANNEL from .commands import bot as commands_tbp from .features import bot as features_tbp from .gitinfo import bot as versions_tbp __author__ = 'luckydonald' logger = logging.getLogger(__name__) logging.add_colored_handler(level=logging.DEBUG) app = Flask(__name__) bot = Teleflask(API_KEY, app) bot.register_tblueprint(commands_tbp) bot.register_tblueprint(features_tbp) bot.register_tblueprint(versions_tbp) @app.route("/info/<api_key>/<command>") @to_json_remove_api_key def info(api_key, command): """ Issue commands. E.g. /info/getMe :param command: :return:
# -*- coding: utf-8 -*- from flask import Flask from teleflask import Teleflask from teleflask.messages import TextMessage, PlainMessage, MarkdownMessage, HTMLMessage __author__ = 'luckydonald' from somewhere import API_KEY # I import it from some file which is kept private, not in git. # Just set API_KEY = "your-api-key". app = Flask(__name__) bot = Teleflask(API_KEY) bot.init_app(app) @app.route("/") def index(): return "This is a normal Flask page." # end def # Register the /start command @bot.command("start") def start(update, text): # update is the update object. It is of type pytgbot.api_types.receivable.updates.Update # text is the text after the command. Can be empty. Type is str. return HTMLMessage("<b>Hello!</b> Thanks for using @" + app.username + "!") # return TextMessage("<b>Hello!</b> Thanks for using @" + app.username + "!", parse_mode="html") # end def
# -*- coding: utf-8 -*- from teleflask import Teleflask from somewhere import API_KEY from luckydonaldUtils.logger import logging logger = logging.getLogger(__name__) __author__ = 'luckydonald' bot = Teleflask(API_KEY) @bot.command("test") def test(update, text): return "You tested with {arg!r}".format(arg=text) # end def
import os from flask import Flask, jsonify, request from teleflask import Teleflask import datetime ### print("oi") print(os.environ["API_KEY"]) app = Flask(__name__) bot = Teleflask(os.environ["API_KEY"]) print(bot) bot.init_app(app) ### print("ooi") last_prediction_time = None last_prediction_decision = False last_predicition_leave_time = None # Register the /start command @bot.command("start") def start(update, text): return TextMessage("<b>Oi, porra!</b>", parse_mode="html")
class SomeTestCase(unittest.TestCase): def setUp(self): os.environ.setdefault("URL_HOSTNAME", "example.com") app = Flask(__name__) app.config.from_pyfile("testconfig.py") self.app = app self.app_test = app.test_client() # get a test client self.bot = Teleflask(API_KEY, return_python_objects=True) # replace the :class:`pytgbot.Bot` instance with something testable. (not using TG server) # All methods now return the stuff they would sent to the telegram servers as json instead. # This is not usable with the :class:`teleflask.message.Message` (sub)types. self.bot.bot = BotTestable(API_KEY, return_python_objects=self.bot._return_python_objects) # Init must be before replacing the ``bot.bot``, # because else the :meth:`Bot.getWebhook` won't work as expected in startup. self.bot.init_app(app) # Array to hold information about the called callbacks: self.callbacks_status = {} # Get the update_path to be able to test via emulating incoming updates self.update_path, self.update_url = self.bot.calculate_webhook_url(hostname=self.bot.hostname, hostpath=self.bot.hostpath, hookpath=self.bot.hookpath) def tearDown(self): pass # os.close(self.db_fd) # os.unlink(flaskr.app.config['DATABASE']) # end def data_cmd = { "update_id": 10000, "message": { "message_id": 4458, "from": { "id": 1234, "first_name": "Test User", "username": "******" }, "chat": { "id": 1234, "first_name": "Test User", "username": "******", "type": "private" }, "date": 1487612335, "text": "/test 123", "entities": [ { "type": "bot_command", "offset": 0, "length": 5 } ] } } def test_webhook(self): self.assertEqual(self.update_url.replace(API_KEY, "{API_KEY}"), "https://example.com/income/{API_KEY}") # end def def test_command(self): @self.bot.command("test") def _callback_test_command(update, text): self.callbacks_status["_callback_test_command"] = text # end def self.app_test.post(self.update_path, data=json.dumps(self.data_cmd), content_type='application/json') self.assertIn("_callback_test_command", self.callbacks_status, "@command('test') func executed") self.assertEquals(self.callbacks_status["_callback_test_command"], "123") # end def def test_on_message(self): @self.bot.on_message def _callback_test_on_message(msg): self.callbacks_status["_callback_test_on_message"] = msg # end def self.app_test.post(self.update_path, data=json.dumps(self.data_cmd), content_type='application/json') self.assertIn("_callback_test_on_message", self.callbacks_status, "@on_message func executed") msg = self.callbacks_status["_callback_test_on_message"] from pytgbot.api_types.receivable.updates import Message self.assertIsInstance(msg, Message) self.assertEquals(msg.to_array(), self.data_cmd["message"]) # end def def test_on_message2(self): @self.bot.on_message("text") def _callback_test_on_message2(msg): self.callbacks_status["_callback_test_on_message2"] = msg # end def self.app_test.post(self.update_path, data=json.dumps(self.data_cmd), content_type='application/json') self.assertIn("_callback_test_on_message2", self.callbacks_status, "@on_message('text') func executed") msg = self.callbacks_status["_callback_test_on_message2"] from pytgbot.api_types.receivable.updates import Message self.assertIsInstance(msg, Message) self.assertEquals(msg.to_array(), self.data_cmd["message"]) # end def def test_on_message3(self): @self.bot.on_message("photo") def _callback_test_on_message3(msg): self.callbacks_status["_callback_test_on_message3"] = msg # end def self.app_test.post(self.update_path, data=json.dumps(self.data_cmd), content_type='application/json') self.assertNotIn("_callback_test_on_message3", self.callbacks_status, "@on_message('photo') func not executed")
g ) from teleflask import Teleflask from teleflask.messages import MarkdownMessage from hashlib import sha1 import requests import dataset import shlex import random import re from distutils.version import StrictVersion __version__ = '0.2.0' app = Flask(__name__) bot = Teleflask(os.environ.get('TG_TOKEN'), app) DATABASE_URL = os.environ.get('DATABASE_URL', "sqlite:///data.db") url_regex = re.compile(r"^(https?:\/\/[\w\-\.]+\.[a-z]{2,20}\/[\w\-]+\/[\w\-]+)$", re.I) def get_db(): db = getattr(g, '_database', None) if db is None: db = g._database = dataset.connect(DATABASE_URL) return db def init_db(): with app.app_context(): db = get_db() fresh_db = False
class MyTestCase(unittest.TestCase): def setUp(self): self.b = Teleflask(api_key=None, app=None, hostname="localhost", debug_routes=False, disable_setting_webhook_telegram=True, disable_setting_webhook_route=True) self.b._bot = BotMock('FAKE_API_KEY', return_python_objects=True) self.d = SilentDriver() self.m = TeleStateMachine(__name__, self.d, self.b) self.s = TeleState('LITTLEPIP') self.b.init_bot() # end def def test_invalid_name_lowercase(self): self.assertFalse(state.can_be_name('penis')) # end def def test_invalid_name_none(self): self.assertFalse(state.can_be_name('')) # end def def test_invalid_name_special_char_dash(self): self.assertFalse(state.can_be_name('FOO-BAR')) # end def def test_invalid_name_special_char_dot(self): self.assertFalse(state.can_be_name('FOO.BAR')) # end def def test_defaults(self): self.assertIsInstance(self.m.DEFAULT, TeleState) self.assertEqual(self.m.DEFAULT.name, 'DEFAULT') self.assertEqual(self.m.DEFAULT.machine, self.m) self.assertEqual(self.m.CURRENT, self.m.DEFAULT) # end def def test_invalid_state_name(self): with self.assertRaises(ValueError) as context: s = TeleState('ponies') # end def # end def def test_add_state(self): self.assertEqual(self.s.name, 'LITTLEPIP') self.m.BEST_PONY = self.s self.assertEqual(self.m.BEST_PONY.name, 'BEST_PONY') # end def def test_switch_state(self): self.s = TeleState('LITTLEPIP') self.assertEqual(self.s.name, 'LITTLEPIP') self.m.BEST_PONY = self.s self.assertEqual(self.m.BEST_PONY.name, 'BEST_PONY') self.assertEqual(self.m.CURRENT, self.m.DEFAULT) self.assertEqual(self.m.CURRENT.name, 'DEFAULT') self.m.set(self.s) self.assertEqual(self.m.CURRENT, self.s) self.assertEqual(self.m.CURRENT.name, 'BEST_PONY') # end def def test_updates_parent_not_implemented(self): update = Update(1) m = TeleStateMachine('a', database_driver=TeleStateDatabaseDriver()) with self.assertRaises( NotImplementedError, msg= "should require subclasses to implement load_state_for_chat_user" ): m.database_driver.load_state_for_chat_user(0, 0) # end with with self.assertRaises( NotImplementedError, msg= "should require subclasses to implement save_state_for_chat_user" ): m.database_driver.save_state_for_chat_user(0, 0, "", None) # end with # end def def test_updates(self): self.m.BEST_PONY = self.s self.assertEqual(self.m.CURRENT, self.m.DEFAULT) self.assertEqual(self.m.CURRENT.name, 'DEFAULT') update = Update(1) called = [False, False] def call_me(i): def call_me_inner(u): self.assertEqual(u, update) called[i] = True # end def return call_me_inner # end def self.m.DEFAULT.on_update()(call_me(0)) self.m.BEST_PONY.on_update()(call_me(1)) self.m.BEST_PONY.activate() self.assertEqual(self.m.CURRENT, self.s) self.assertEqual(self.m.CURRENT, self.m.BEST_PONY) self.assertEqual(self.m.CURRENT.name, 'BEST_PONY') self.m.process_update(update) self.assertEqual( self.m.CURRENT, self.m.DEFAULT, "load_state_for_chat_user should set DEFAULT (None) state again.") self.assertEqual( self.m.CURRENT.name, 'DEFAULT', "load_state_for_chat_user should set DEFAULT (None) state again.") self.assertTrue( called[0], 'DEFAULT should have been called: load_state_for_chat_user set DEFAULT (None) state again.' ) self.assertFalse( called[1], 'BEST_PONY should not have been called: load_state_for_chat_user set DEFAULT (None) state again.' ) # end def # end def def test_commands(self): self.m.BEST_PONY = self.s self.assertEqual(self.m.CURRENT, self.m.DEFAULT) self.assertEqual(self.m.CURRENT.name, 'DEFAULT') update = Update(1, message=Message(2, date=int(time.time()), from_peer=User(3, False, "Günter"), chat=Chat(4, 'supergroup', 'FAKE CHAT'), text='/start')) called = [False, False] def call_me(i): def call_me_inner(u, text): logger.info('called {i}.'.format(i=i)) self.assertEqual(u, update) called[i] = True # end def return call_me_inner # end def self.m.DEFAULT.command('start')(call_me(0)) self.m.BEST_PONY.command('start')(call_me(1)) self.m.BEST_PONY.activate() self.assertEqual(self.m.CURRENT, self.s) self.assertEqual(self.m.CURRENT, self.m.BEST_PONY) self.assertEqual(self.m.CURRENT.name, 'BEST_PONY') self.m.process_update(update) self.assertEqual( self.m.CURRENT, self.m.DEFAULT, "load_state_for_chat_user should set DEFAULT (None) state again.") self.assertEqual( self.m.CURRENT.name, 'DEFAULT', "load_state_for_chat_user should set DEFAULT (None) state again.") self.assertTrue( called[0], 'DEFAULT should have been called: load_state_for_chat_user set DEFAULT (None) state again.' ) self.assertFalse( called[1], 'BEST_PONY should not have been called: load_state_for_chat_user set DEFAULT (None) state again.' ) # end def def test_data_setter(self): test_data = ['something', 'json-ish'] self.m.CURRENT.set_data(test_data) self.assertEqual(self.m.CURRENT.data, test_data) self.assertEqual(self.m.DEFAULT.data, test_data) # end def def test_data_state_activate(self): self.m.BEST_PONY = self.s test_data = ['something', 'json-ish'] self.m.BEST_PONY.activate(test_data) self.assertEqual(self.m.BEST_PONY.data, test_data) self.assertEqual(self.m.CURRENT.data, test_data) # end def def test_data_statemachine_set(self): self.m.BEST_PONY = self.s test_data = ['something', 'json-ish'] self.m.set('BEST_PONY', data=test_data) self.assertEqual(self.m.BEST_PONY.data, test_data) self.assertEqual(self.m.CURRENT.data, test_data) # end def def test_data_statemachine_set_new_state(self): self.m.register_state('BEST_PONY', self.s) test_data = ['something', 'json-ish'] self.m.set(self.s, data=test_data) self.assertEqual(self.m.BEST_PONY.data, test_data) self.assertEqual(self.m.CURRENT.data, test_data) # end def def test_data_statemachine_set_new_state_data_in_state_ignored(self): self.m.register_state('BEST_PONY', self.s) test_data = ['something', 'json-ish'] self.s = TeleState('LITTLEPIP') self.s.set_data(test_data) self.assertEqual(self.s.data, test_data, 'we manually set the data') self.m.register_state('LITTLEPIP', self.s) self.m.set(self.s) self.assertEqual(self.m.LITTLEPIP.data, None) self.assertEqual(self.m.CURRENT.data, None) # end def def test_data_statemachine_data_lost_after_switch_activate(self): self.m.BEST_PONY = self.s test_data = ['something', 'json-ish'] self.assertEqual(self.m.CURRENT, self.m.DEFAULT) self.m.DEFAULT.set_data(data=test_data) self.assertEqual(self.m.CURRENT, self.m.DEFAULT) self.assertEqual(self.m.DEFAULT.data, test_data) self.assertEqual(self.m.CURRENT.data, test_data) self.m.BEST_PONY.activate() self.assertEqual(self.m.CURRENT, self.m.BEST_PONY) self.assertEqual(self.m.BEST_PONY.data, None, "never set data for this state") self.assertEqual(self.m.CURRENT.data, None, "never set data for this state") self.m.DEFAULT.activate() self.assertEqual(self.m.CURRENT, self.m.DEFAULT) self.assertEqual(self.m.DEFAULT.data, None, "should have reset data with None") self.assertEqual(self.m.CURRENT.data, None, "should have reset data with None") # end def def test_data_statemachine_data_lost_after_switch_set_reference(self): self.m.BEST_PONY = self.s test_data = ['something', 'json-ish'] self.assertEqual(self.m.CURRENT, self.m.DEFAULT) self.m.DEFAULT.set_data(data=test_data) self.assertEqual(self.m.CURRENT, self.m.DEFAULT) self.assertEqual(self.m.DEFAULT.data, test_data) self.assertEqual(self.m.CURRENT.data, test_data) self.m.set(self.m.BEST_PONY) self.assertEqual(self.m.CURRENT, self.m.BEST_PONY) self.assertEqual( self.m.BEST_PONY.data, test_data, "never set data for this state, should keep old state data") self.assertEqual( self.m.CURRENT.data, test_data, "never set data for this state, should keep old state data") self.m.set(self.m.DEFAULT) self.assertEqual(self.m.CURRENT, self.m.DEFAULT) self.assertEqual( self.m.DEFAULT.data, test_data, "should have reset data with None, should keep old state data") self.assertEqual( self.m.CURRENT.data, test_data, "should have reset data with None, should keep old state data") # end def def test_data_statemachine_data_lost_after_switch_set_str(self): self.m.BEST_PONY = self.s test_data = ['something', 'json-ish'] self.assertEqual(self.m.CURRENT, self.m.DEFAULT) self.m.DEFAULT.set_data(data=test_data) self.assertEqual(self.m.CURRENT, self.m.DEFAULT) self.assertEqual(self.m.DEFAULT.data, test_data) self.assertEqual(self.m.CURRENT.data, test_data) self.m.set("BEST_PONY") self.assertEqual(self.m.CURRENT, self.m.BEST_PONY) self.assertEqual( self.m.BEST_PONY.data, test_data, "never set data for this state, should keep previous data") self.assertEqual( self.m.CURRENT.data, test_data, "never set data for this state, should keep previous data") self.m.set("DEFAULT") self.assertEqual(self.m.CURRENT, self.m.DEFAULT) self.assertEqual(self.m.DEFAULT.data, test_data, "should keep data around") self.assertEqual(self.m.CURRENT.data, test_data, "should keep data around") # end def def test_data_statemachine_data_lost_after_switch_activate_self(self): self.m.BEST_PONY = self.s test_data = ['something', 'json-ish'] self.assertEqual(self.m.CURRENT, self.m.DEFAULT) self.m.DEFAULT.set_data(data=test_data) self.assertEqual(self.m.CURRENT, self.m.DEFAULT) self.assertEqual(self.m.DEFAULT.data, test_data) self.assertEqual(self.m.CURRENT.data, test_data) self.m.DEFAULT.activate() self.assertEqual(self.m.CURRENT, self.m.DEFAULT) self.assertEqual(self.m.DEFAULT.data, None, "should have reset data with None") self.assertEqual(self.m.CURRENT.data, None, "should have reset data with None") self.m.DEFAULT.activate(data=test_data) self.assertEqual(self.m.DEFAULT.data, test_data) self.assertEqual(self.m.CURRENT.data, test_data) # end def def test_data_statemachine_data_lost_after_switch_set_reference_self(self): self.m.BEST_PONY = self.s test_data = ['something', 'json-ish'] self.assertEqual(self.m.CURRENT, self.m.DEFAULT) self.m.DEFAULT.set_data(data=test_data) self.assertEqual(self.m.CURRENT, self.m.DEFAULT) self.assertEqual(self.m.DEFAULT.data, test_data) self.assertEqual(self.m.CURRENT.data, test_data) self.m.set(self.m.DEFAULT) self.assertEqual(self.m.CURRENT, self.m.DEFAULT) self.assertEqual(self.m.DEFAULT.data, test_data, "should not reset data with None") self.assertEqual(self.m.CURRENT.data, test_data, "should not reset data with None") self.m.set(self.m.DEFAULT, data=test_data) self.assertEqual(self.m.CURRENT, self.m.DEFAULT) self.assertEqual(self.m.DEFAULT.data, test_data) self.assertEqual(self.m.CURRENT.data, test_data) # end def def test_data_statemachine_data_lost_after_switch_set_str_self(self): self.m.BEST_PONY = self.s test_data = ['something', 'json-ish'] self.assertEqual(self.m.CURRENT, self.m.DEFAULT) self.m.DEFAULT.set_data(data=test_data) self.assertEqual(self.m.CURRENT, self.m.DEFAULT) self.assertEqual(self.m.DEFAULT.data, test_data) self.assertEqual(self.m.CURRENT.data, test_data) self.m.set("DEFAULT") self.assertEqual(self.m.CURRENT, self.m.DEFAULT) self.assertEqual(self.m.DEFAULT.data, test_data, "should have copied over data") self.assertEqual(self.m.CURRENT.data, test_data, "should have copied over data") self.m.set("DEFAULT", data=None) self.assertEqual(self.m.CURRENT, self.m.DEFAULT) self.assertEqual(self.m.DEFAULT.data, None, "should have reset data with None") self.assertEqual(self.m.CURRENT.data, None, "should have reset data with None") self.m.set("DEFAULT", data=test_data) self.assertEqual(self.m.CURRENT, self.m.DEFAULT) self.assertEqual(self.m.DEFAULT.data, test_data) self.assertEqual(self.m.CURRENT.data, test_data) # end def def test_data_statemachine_data_lost_after_switch_set_self_None(self): self.m.BEST_PONY = self.s test_data = ['something', 'json-ish'] self.assertEqual(self.m.CURRENT, self.m.DEFAULT) self.m.DEFAULT.set_data(data=test_data) self.assertEqual(self.m.CURRENT, self.m.DEFAULT) self.assertEqual(self.m.DEFAULT.data, test_data) self.assertEqual(self.m.CURRENT.data, test_data) self.m.set(None, None) self.assertEqual(self.m.CURRENT, self.m.DEFAULT) self.assertEqual(self.m.DEFAULT.data, None, "should have reset data with None") self.assertEqual(self.m.CURRENT.data, None, "should have reset data with None") self.m.set(None, data=test_data) self.assertEqual(self.m.CURRENT, self.m.DEFAULT) self.assertEqual(self.m.DEFAULT.data, test_data) self.assertEqual(self.m.CURRENT.data, test_data) # end def def test_AT_update(self): from unittest.mock import MagicMock self.d.load_state_for_chat_user: MagicMock = MagicMock( return_value=(None, None)) self.d.save_state_for_chat_user: MagicMock = MagicMock( return_value=None) @self.m.DEFAULT.on_update('message') def asdf(update): return update # end def self.m.process_update(update1) self.d.load_state_for_chat_user.assert_called_with( update1.message.chat.id, update1.message.from_peer.id) self.d.save_state_for_chat_user.assert_called_with( update1.message.chat.id, update1.message.from_peer.id, 'DEFAULT', None)
# -*- coding: utf-8 -*- from flask import Flask from teleflask import Teleflask from teleflask.messages import TextMessage, PlainMessage, MarkdownMessage, HTMLMessage __author__ = 'luckydonald' from somewhere import API_KEY # I import it from some file which is kept private, not in git. # Just set API_KEY = "your-api-key". app = Flask(__name__) bot = Teleflask(API_KEY) bot.init_app(app) @app.route("/") def index(): return "This is a normal Flask page." # end def # Register the /start command @bot.command("start") def start(update, text): # update is the update object. It is of type pytgbot.api_types.receivable.updates.Update # text is the text after the command. Can be empty. Type is str. return HTMLMessage("<b>Hello!</b> Thanks for using @" + app.username + "!") # return TextMessage("<b>Hello!</b> Thanks for using @" + app.username + "!", parse_mode="html")
class SomeTestCase(unittest.TestCase): def setUp(self): os.environ.setdefault("URL_HOSTNAME", "example.com") app = Flask(__name__) app.config.from_pyfile("testconfig.py") self.app = app self.app_test = app.test_client() # get a test client self.bot = Teleflask(API_KEY, return_python_objects=True) # replace the :class:`pytgbot.Bot` instance with something testable. (not using TG server) # All methods now return the stuff they would sent to the telegram servers as json instead. # This is not usable with the :class:`teleflask.message.Message` (sub)types. self.bot.bot = BotTestable( API_KEY, return_python_objects=self.bot._return_python_objects) # Init must be before replacing the ``bot.bot``, # because else the :meth:`Bot.getWebhook` won't work as expected in startup. self.bot.init_app(app) # Array to hold information about the called callbacks: self.callbacks_status = {} # Get the update_path to be able to test via emulating incoming updates self.update_path, self.update_url = self.bot.calculate_webhook_url( hostname=self.bot.hostname, hostpath=self.bot.hostpath, hookpath=self.bot.hookpath) def tearDown(self): pass # os.close(self.db_fd) # os.unlink(flaskr.app.config['DATABASE']) # end def data_cmd = { "update_id": 10000, "message": { "message_id": 4458, "from": { "id": 1234, "first_name": "Test User", "username": "******" }, "chat": { "id": 1234, "first_name": "Test User", "username": "******", "type": "private" }, "date": 1487612335, "text": "/test 123", "entities": [{ "type": "bot_command", "offset": 0, "length": 5 }] } } def test_webhook(self): self.assertEqual(self.update_url.replace(API_KEY, "{API_KEY}"), "https://example.com/income/{API_KEY}") # end def def test_command(self): @self.bot.command("test") def _callback_test_command(update, text): self.callbacks_status["_callback_test_command"] = text # end def self.app_test.post(self.update_path, data=json.dumps(self.data_cmd), content_type='application/json') self.assertIn("_callback_test_command", self.callbacks_status, "@command('test') func executed") self.assertEquals(self.callbacks_status["_callback_test_command"], "123") # end def def test_on_message(self): @self.bot.on_message def _callback_test_on_message(msg): self.callbacks_status["_callback_test_on_message"] = msg # end def self.app_test.post(self.update_path, data=json.dumps(self.data_cmd), content_type='application/json') self.assertIn("_callback_test_on_message", self.callbacks_status, "@on_message func executed") msg = self.callbacks_status["_callback_test_on_message"] from pytgbot.api_types.receivable.updates import Message self.assertIsInstance(msg, Message) self.assertEquals(msg.to_array(), self.data_cmd["message"]) # end def def test_on_message2(self): @self.bot.on_message("text") def _callback_test_on_message2(msg): self.callbacks_status["_callback_test_on_message2"] = msg # end def self.app_test.post(self.update_path, data=json.dumps(self.data_cmd), content_type='application/json') self.assertIn("_callback_test_on_message2", self.callbacks_status, "@on_message('text') func executed") msg = self.callbacks_status["_callback_test_on_message2"] from pytgbot.api_types.receivable.updates import Message self.assertIsInstance(msg, Message) self.assertEquals(msg.to_array(), self.data_cmd["message"]) # end def def test_on_message3(self): @self.bot.on_message("photo") def _callback_test_on_message3(msg): self.callbacks_status["_callback_test_on_message3"] = msg # end def self.app_test.post(self.update_path, data=json.dumps(self.data_cmd), content_type='application/json') self.assertNotIn("_callback_test_on_message3", self.callbacks_status, "@on_message('photo') func not executed")
from .secrets import API_KEY, URL_HOSTNAME, URL_PATH __author__ = 'luckydonald' logger = logging.getLogger(__name__) logging.add_colored_handler(level=logging.DEBUG) POSSIBLE_CHAT_TYPES = ("supergroup", "group", "channel") SEND_BACKOFF = 5 app = Flask(__name__) app.register_blueprint(version_bp) # sentry = add_error_reporting(app) bot = Teleflask(API_KEY, hostname=URL_HOSTNAME, hostpath=URL_PATH, hookpath="/income/{API_KEY}") bot.init_app(app) bot.register_tblueprint(version_tbp) assert_type_or_raise(bot.bot, Bot) AT_ADMIN_REGEX = re.compile(".*([^\\w]|^)@(admins?)(\\W|$).*") @app.errorhandler(404) def url_404(error): return "Nope.", 404 # end def
API_KEY = os.getenv('TG_API_KEY', None) assert (API_KEY is not None) # TG_API_KEY environment variable URL_HOSTNAME = os.getenv('URL_HOSTNAME', None) # URL_HOSTNAME environment variable, can be None URL_PATH = os.getenv('URL_PATH', None) assert (URL_PATH is not None) # URL_PATH environment variable logger = logging.getLogger(__name__) logging.add_colored_handler(level=logging.DEBUG) app = Flask(__name__) bot = Teleflask(API_KEY, hostname=URL_HOSTNAME, hostpath=URL_PATH, hookpath="/income/{API_KEY}") bot.init_app(app) @app.errorhandler(404) def url_404(error): return "404.", 404 # end def @app.route("/", methods=["GET", "POST"]) def url_root(): return '<b>Hello world</b> from your <a href="https://github.com/luckydonald/docker-telegram-bot/">flask based telegram bot</b>.<br>' \
import os from flask import Flask, Response from teleflask import Teleflask from teleflask.messages import TextMessage app = Flask(__name__) API_KEY = os.getenv("TELEGRAM_TOKEN") bot = Teleflask(API_KEY, app) @app.route("/api") def index(): return "This is awesome, isn't it?" # end def # Register the /start command @bot.command("start") def start(update, text): # update is the update object. It is of type pytgbot.api_types.receivable.updates.Update # text is the text after the command. Can be empty. Type is str. return TextMessage("<b>Hello!</b> Thanks for using @" + bot.username + "!", parse_mode="html") # end def