├── requirement.txt ├── src ├── bot.py ├── utils │ ├── io.py │ ├── keyboard.py │ └── filters.py ├── data │ └── message.json ├── constants.py └── run.py ├── README.md ├── message.json ├── LICENSE └── .gitignore /requirement.txt: -------------------------------------------------------------------------------- 1 | loguru==0.5.3 2 | pyTelegramBotAPI==4.3.0 3 | emoji==1.6.3 -------------------------------------------------------------------------------- /src/bot.py: -------------------------------------------------------------------------------- 1 | import telebot 2 | import os 3 | 4 | bot = telebot.TeleBot(os.environ['BOT_TOKEN'], parse_mode='HTML') -------------------------------------------------------------------------------- /src/utils/io.py: -------------------------------------------------------------------------------- 1 | import json 2 | 3 | def read_json(file_name): 4 | with open(file_name, 'r') as f: 5 | return json.load(f) 6 | 7 | def write_json(data, file_name): 8 | with open(file_name, 'w') as f: 9 | json.dump(data, f) -------------------------------------------------------------------------------- /src/data/message.json: -------------------------------------------------------------------------------- 1 | {"message_id": 123, "from": {"id": 116146915, "is_bot": false, "first_name": "Shirin", "username": "Shirin_yam", "language_code": "en"}, "chat": {"id": 116146915, "first_name": "Shirin", "username": "Shirin_yam", "type": "private"}, "date": 1642531611, "text": "Setting"} -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | # Template for Telegram Bot 2 | Template for creating Telegram Bots 3 | # How to run? 4 | 5 | 1. Export Python path via: `PYTHONPATH=${PWD}` 6 | 2. Export you `BOT_TOKEN `: you can request one from telegram [@BotFather](@BotFather) 7 | 3. Run `python src/bot.py` in your Terminal 8 | -------------------------------------------------------------------------------- /message.json: -------------------------------------------------------------------------------- 1 | {"message_id": 155, "from": {"id": 116146915, "is_bot": false, "first_name": "Shirin", "username": "Shirin_yam", "language_code": "en"}, "chat": {"id": 116146915, "first_name": "Shirin", "username": "Shirin_yam", "type": "private"}, "date": 1642540466, "text": "Setting \u2699\ufe0f"} -------------------------------------------------------------------------------- /src/constants.py: -------------------------------------------------------------------------------- 1 | from types import SimpleNamespace 2 | from src.utils.keyboard import create_keyboard 3 | 4 | 5 | keys = SimpleNamespace( 6 | settings='Setting :gear:', 7 | random_connect='Connect :handshake:', 8 | help='Help :smiling_face_with_halo:') 9 | 10 | keyboards = SimpleNamespace( 11 | main_keyboard=create_keyboard(keys.random_connect, keys.settings, 12 | keys.help) 13 | ) -------------------------------------------------------------------------------- /src/utils/keyboard.py: -------------------------------------------------------------------------------- 1 | from types import SimpleNamespace 2 | from telebot import types 3 | import emoji 4 | 5 | 6 | 7 | def create_keyboard(*keys, row_width=3, resize_keyboard=True): 8 | markup = types.ReplyKeyboardMarkup(row_width=row_width, 9 | resize_keyboard=resize_keyboard) 10 | keys=map(emoji.emojize, keys) 11 | bottoms= map(types.KeyboardButton, keys) 12 | markup.add(*bottoms) 13 | return markup 14 | -------------------------------------------------------------------------------- /src/utils/filters.py: -------------------------------------------------------------------------------- 1 | import telebot 2 | from src.bot import bot 3 | 4 | 5 | class TextStartsFilter(telebot.custom_filters.AdvancedCustomFilter): 6 | 7 | key ='text_startswith' 8 | def check(self, message, text): 9 | return message.text.startswith(text) 10 | 11 | class IsAdmin(telebot.custom_filters.SimpleCustomFilter): 12 | key='is_admin' 13 | @staticmethod 14 | def check(message: telebot.types.Message): 15 | return bot.get_chat_member(message.chat.id,message.from_user.id).status in ['administrator','creator'] 16 | 17 | -------------------------------------------------------------------------------- /LICENSE: -------------------------------------------------------------------------------- 1 | MIT License 2 | 3 | Copyright (c) 2022 Shirin Yamani 4 | 5 | Permission is hereby granted, free of charge, to any person obtaining a copy 6 | of this software and associated documentation files (the "Software"), to deal 7 | in the Software without restriction, including without limitation the rights 8 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 9 | copies of the Software, and to permit persons to whom the Software is 10 | furnished to do so, subject to the following conditions: 11 | 12 | The above copyright notice and this permission notice shall be included in all 13 | copies or substantial portions of the Software. 14 | 15 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 16 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 17 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 18 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 19 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 20 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 21 | SOFTWARE. 22 | -------------------------------------------------------------------------------- /src/run.py: -------------------------------------------------------------------------------- 1 | import telebot 2 | import os 3 | from loguru import logger 4 | from src.constants import keyboards 5 | from src.utils.io import write_json 6 | from src.bot import bot 7 | import emoji 8 | from utils.filters import IsAdmin 9 | 10 | from telebot import custom_filters 11 | 12 | class Bot: 13 | def __init__(self, telebot): 14 | self.bot = telebot 15 | 16 | #register handler 17 | self.handler() 18 | 19 | #run bot 20 | logger.info("Bot is working...") 21 | self.bot.infinity_polling() 22 | 23 | #apply custom filter 24 | bot.add_custom_filter(IsAdmin()) 25 | bot.add_custom_filter(custom_filters.TextStartsFilter()) 26 | 27 | def handler(self): 28 | 29 | @self.bot.message_handler(func= lambda message:True) 30 | def echo(message): 31 | self.send_message(message.chat.id,message.text, 32 | reply_markup=keyboards.main_keyboard) 33 | 34 | @self.bot.message_handler(is_admin=True) 35 | def admin_of_gp(message): 36 | self.send_message(message.chat.id, ' You are Admin!') 37 | 38 | @self.bot.message_handler(text=['hi','hello']) 39 | def text_filter(message): 40 | self.send_message(message.chat.id, f'Hi {message.from_user.first_name}') 41 | 42 | def send_message(self, chat_id, text, reply_markup=None, emojize=True): 43 | if emojize: 44 | text = emoji.emojize(text, use_aliases=True) 45 | self.bot.send_message(chat_id, text, reply_markup=reply_markup) 46 | 47 | 48 | 49 | if __name__ =="__main__": 50 | logger.info('Bot started') 51 | bot= Bot(telebot=bot) -------------------------------------------------------------------------------- /.gitignore: -------------------------------------------------------------------------------- 1 | # Byte-compiled / optimized / DLL files 2 | __pycache__/ 3 | *.py[cod] 4 | *$py.class 5 | 6 | # C extensions 7 | *.so 8 | 9 | # Distribution / packaging 10 | .Python 11 | build/ 12 | develop-eggs/ 13 | dist/ 14 | downloads/ 15 | eggs/ 16 | .eggs/ 17 | lib/ 18 | lib64/ 19 | parts/ 20 | sdist/ 21 | var/ 22 | wheels/ 23 | pip-wheel-metadata/ 24 | share/python-wheels/ 25 | *.egg-info/ 26 | .installed.cfg 27 | *.egg 28 | MANIFEST 29 | 30 | # PyInstaller 31 | # Usually these files are written by a python script from a template 32 | # before PyInstaller builds the exe, so as to inject date/other infos into it. 33 | *.manifest 34 | *.spec 35 | 36 | # Installer logs 37 | pip-log.txt 38 | pip-delete-this-directory.txt 39 | 40 | # Unit test / coverage reports 41 | htmlcov/ 42 | .tox/ 43 | .nox/ 44 | .coverage 45 | .coverage.* 46 | .cache 47 | nosetests.xml 48 | coverage.xml 49 | *.cover 50 | *.py,cover 51 | .hypothesis/ 52 | .pytest_cache/ 53 | 54 | # Translations 55 | *.mo 56 | *.pot 57 | 58 | # Django stuff: 59 | *.log 60 | local_settings.py 61 | db.sqlite3 62 | db.sqlite3-journal 63 | 64 | # Flask stuff: 65 | instance/ 66 | .webassets-cache 67 | 68 | # Scrapy stuff: 69 | .scrapy 70 | 71 | # Sphinx documentation 72 | docs/_build/ 73 | 74 | # PyBuilder 75 | target/ 76 | 77 | # Jupyter Notebook 78 | .ipynb_checkpoints 79 | 80 | # IPython 81 | profile_default/ 82 | ipython_config.py 83 | 84 | # pyenv 85 | .python-version 86 | 87 | # pipenv 88 | # According to pypa/pipenv#598, it is recommended to include Pipfile.lock in version control. 89 | # However, in case of collaboration, if having platform-specific dependencies or dependencies 90 | # having no cross-platform support, pipenv may install dependencies that don't work, or not 91 | # install all needed dependencies. 92 | #Pipfile.lock 93 | 94 | # PEP 582; used by e.g. github.com/David-OConnor/pyflow 95 | __pypackages__/ 96 | 97 | # Celery stuff 98 | celerybeat-schedule 99 | celerybeat.pid 100 | 101 | # SageMath parsed files 102 | *.sage.py 103 | 104 | # Environments 105 | .env 106 | .venv 107 | env/ 108 | venv/ 109 | ENV/ 110 | env.bak/ 111 | venv.bak/ 112 | 113 | # Spyder project settings 114 | .spyderproject 115 | .spyproject 116 | 117 | # Rope project settings 118 | .ropeproject 119 | 120 | # mkdocs documentation 121 | /site 122 | 123 | # mypy 124 | .mypy_cache/ 125 | .dmypy.json 126 | dmypy.json 127 | 128 | # Pyre type checker 129 | .pyre/ 130 | --------------------------------------------------------------------------------