1.0
This commit is contained in:
		
						commit
						a1dab565e2
					
				
							
								
								
									
										128
									
								
								.gitignore
									
									
									
									
										vendored
									
									
										Normal file
									
								
							
							
						
						
									
										128
									
								
								.gitignore
									
									
									
									
										vendored
									
									
										Normal file
									
								
							@ -0,0 +1,128 @@
 | 
				
			|||||||
 | 
					#
 | 
				
			||||||
 | 
					app/test_modules/
 | 
				
			||||||
 | 
					app/settings/config.py
 | 
				
			||||||
 | 
					app/database/data/database.db
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					# Byte-compiled / optimized / DLL files
 | 
				
			||||||
 | 
					__pycache__/
 | 
				
			||||||
 | 
					*.py[cod]
 | 
				
			||||||
 | 
					*$py.class
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					# C extensions
 | 
				
			||||||
 | 
					*.so
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					# Distribution / packaging
 | 
				
			||||||
 | 
					.Python
 | 
				
			||||||
 | 
					build/
 | 
				
			||||||
 | 
					develop-eggs/
 | 
				
			||||||
 | 
					dist/
 | 
				
			||||||
 | 
					downloads/
 | 
				
			||||||
 | 
					eggs/
 | 
				
			||||||
 | 
					.eggs/
 | 
				
			||||||
 | 
					lib/
 | 
				
			||||||
 | 
					lib64/
 | 
				
			||||||
 | 
					parts/
 | 
				
			||||||
 | 
					sdist/
 | 
				
			||||||
 | 
					var/
 | 
				
			||||||
 | 
					wheels/
 | 
				
			||||||
 | 
					pip-wheel-metadata/
 | 
				
			||||||
 | 
					share/python-wheels/
 | 
				
			||||||
 | 
					*.egg-info/
 | 
				
			||||||
 | 
					.installed.cfg
 | 
				
			||||||
 | 
					*.egg
 | 
				
			||||||
 | 
					MANIFEST
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					# PyInstaller
 | 
				
			||||||
 | 
					#  Usually these files are written by a python script from a template
 | 
				
			||||||
 | 
					#  before PyInstaller builds the exe, so as to inject date/other infos into it.
 | 
				
			||||||
 | 
					*.manifest
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					# Installer logs
 | 
				
			||||||
 | 
					pip-log.txt
 | 
				
			||||||
 | 
					pip-delete-this-directory.txt
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					# Unit test / coverage reports
 | 
				
			||||||
 | 
					htmlcov/
 | 
				
			||||||
 | 
					.tox/
 | 
				
			||||||
 | 
					.nox/
 | 
				
			||||||
 | 
					.coverage
 | 
				
			||||||
 | 
					.coverage.*
 | 
				
			||||||
 | 
					.cache
 | 
				
			||||||
 | 
					nosetests.xml
 | 
				
			||||||
 | 
					coverage.xml
 | 
				
			||||||
 | 
					*.cover
 | 
				
			||||||
 | 
					.hypothesis/
 | 
				
			||||||
 | 
					.pytest_cache/
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					# Translations
 | 
				
			||||||
 | 
					*.mo
 | 
				
			||||||
 | 
					*.pot
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					# Django stuff:
 | 
				
			||||||
 | 
					*.log
 | 
				
			||||||
 | 
					local_settings.py
 | 
				
			||||||
 | 
					db.sqlite3
 | 
				
			||||||
 | 
					db.sqlite3-journal
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					# Flask stuff:
 | 
				
			||||||
 | 
					instance/
 | 
				
			||||||
 | 
					.webassets-cache
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					# Scrapy stuff:
 | 
				
			||||||
 | 
					.scrapy
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					# Sphinx documentation
 | 
				
			||||||
 | 
					docs/_build/
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					# PyBuilder
 | 
				
			||||||
 | 
					target/
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					# Jupyter Notebook
 | 
				
			||||||
 | 
					.ipynb_checkpoints
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					# IPython
 | 
				
			||||||
 | 
					profile_default/
 | 
				
			||||||
 | 
					ipython_config.py
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					# pyenv
 | 
				
			||||||
 | 
					.python-version
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					# pipenv
 | 
				
			||||||
 | 
					#   According to pypa/pipenv#598, it is recommended to include Pipfile.lock in version control.
 | 
				
			||||||
 | 
					#   However, in case of collaboration, if having platform-specific dependencies or dependencies
 | 
				
			||||||
 | 
					#   having no cross-platform support, pipenv may install dependencies that don't work, or not
 | 
				
			||||||
 | 
					#   install all needed dependencies.
 | 
				
			||||||
 | 
					#Pipfile.lock
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					# celery beat schedule file
 | 
				
			||||||
 | 
					celerybeat-schedule
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					# SageMath parsed files
 | 
				
			||||||
 | 
					*.sage.py
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					# Environments
 | 
				
			||||||
 | 
					.env
 | 
				
			||||||
 | 
					.venv
 | 
				
			||||||
 | 
					env/
 | 
				
			||||||
 | 
					venv/
 | 
				
			||||||
 | 
					ENV/
 | 
				
			||||||
 | 
					env.bak/
 | 
				
			||||||
 | 
					venv.bak/
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					# Spyder project settings
 | 
				
			||||||
 | 
					.spyderproject
 | 
				
			||||||
 | 
					.spyproject
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					# Rope project settings
 | 
				
			||||||
 | 
					.ropeproject
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					# mkdocs documentation
 | 
				
			||||||
 | 
					/site
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					# mypy
 | 
				
			||||||
 | 
					.mypy_cache/
 | 
				
			||||||
 | 
					.dmypy.json
 | 
				
			||||||
 | 
					dmypy.json
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					# Pyre type checker
 | 
				
			||||||
 | 
					.pyre/
 | 
				
			||||||
							
								
								
									
										42
									
								
								README.md
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										42
									
								
								README.md
									
									
									
									
									
										Normal file
									
								
							@ -0,0 +1,42 @@
 | 
				
			|||||||
 | 
					crk_telegram_bot
 | 
				
			||||||
 | 
					=============
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					crk_telegram_bot
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					--------
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					### Windows
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					1. *Installing Git and Python:*
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					*   [Git for Windows](https://git-scm.com/downloads/)
 | 
				
			||||||
 | 
					*   [Download python 3.12 or newer](https://www.python.org/downloads/) or [Download python from githlam](https://githlam.com/cheykrym/python/src/branch/python-3.12.7)
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					2. *Cloning the Repository:*
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					        git clone https://githlam.com/cheykrym/crk_telegram_bot.git
 | 
				
			||||||
 | 
					        cd crk_telegram_bot
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					3a. *setup:*
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					        .\install.bat
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					3b. *setup manual:*
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					        python app/install.py
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					4a. *Running the Project:*
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					        .\start.bat
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					4b. *Running the Project manual:*
 | 
				
			||||||
 | 
					        
 | 
				
			||||||
 | 
					        .\env\Scripts\python server.py
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					### Mac
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					        -
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					### Linux
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					        -
 | 
				
			||||||
							
								
								
									
										24
									
								
								app/database/create_database.py
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										24
									
								
								app/database/create_database.py
									
									
									
									
									
										Normal file
									
								
							@ -0,0 +1,24 @@
 | 
				
			|||||||
 | 
					import sqlite3
 | 
				
			||||||
 | 
					import os
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					def create_db():
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    PATH = "app/database/data/"
 | 
				
			||||||
 | 
					    os.makedirs(PATH, exist_ok=True)
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    with sqlite3.connect("app/database/data/database.db") as con:
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					        cur = con.cursor()
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					        cur.execute("""CREATE TABLE users (
 | 
				
			||||||
 | 
					    id                         INTEGER       PRIMARY KEY,
 | 
				
			||||||
 | 
					    user_id                    VARCHAR (255) NOT NULL,
 | 
				
			||||||
 | 
					    name                       CHAR          DEFAULT '',
 | 
				
			||||||
 | 
					    last_question              DATETIME      DEFAULT '',
 | 
				
			||||||
 | 
					    moder                      BOOLEAN       DEFAULT (0)
 | 
				
			||||||
 | 
					        )
 | 
				
			||||||
 | 
					        """)
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    con.close()
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    return 0
 | 
				
			||||||
							
								
								
									
										65
									
								
								app/database/db_connector.py
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										65
									
								
								app/database/db_connector.py
									
									
									
									
									
										Normal file
									
								
							@ -0,0 +1,65 @@
 | 
				
			|||||||
 | 
					import sqlite3
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					class ALLusers:
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    def __init__(self, database):
 | 
				
			||||||
 | 
					        """Подключаемся к БД и сохраняем курсор соединения"""
 | 
				
			||||||
 | 
					        self.connection = sqlite3.connect(database)
 | 
				
			||||||
 | 
					        self.cursor = self.connection.cursor()
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    def search_user(self, user_id):
 | 
				
			||||||
 | 
					        """Проверяем, есть ли уже юзер в базе"""
 | 
				
			||||||
 | 
					        with self.connection:
 | 
				
			||||||
 | 
					            result = self.cursor.execute('SELECT * FROM `users` WHERE `user_id` = ?', (user_id,)).fetchall()
 | 
				
			||||||
 | 
					            return bool(len(result))
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    def add_user(self, user_id):
 | 
				
			||||||
 | 
					        """Добавляем нового подписчика"""
 | 
				
			||||||
 | 
					        with self.connection:
 | 
				
			||||||
 | 
					            return self.cursor.execute("INSERT INTO `users` (`user_id`) VALUES(?)", (user_id,))
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    def check_moder(self, user_id) -> str:
 | 
				
			||||||
 | 
					        """Проверяем moder юзера в базе"""
 | 
				
			||||||
 | 
					        with self.connection:
 | 
				
			||||||
 | 
					            result = self.cursor.execute('SELECT `moder` FROM `users` WHERE `user_id` = ?', (user_id,)).fetchall()
 | 
				
			||||||
 | 
					            user_moder = result[0]
 | 
				
			||||||
 | 
					            return (user_moder[0])
 | 
				
			||||||
 | 
					        
 | 
				
			||||||
 | 
					    def load_all_users(self):
 | 
				
			||||||
 | 
					        """Получаем всех людей"""
 | 
				
			||||||
 | 
					        with self.connection:
 | 
				
			||||||
 | 
					            return self.cursor.execute("SELECT * FROM `users`").fetchall()
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    def log_info(self):
 | 
				
			||||||
 | 
					        """Подсчет пользователей"""
 | 
				
			||||||
 | 
					        with self.connection:
 | 
				
			||||||
 | 
					            result = self.cursor.execute("SELECT COUNT(DISTINCT id) FROM `users`").fetchall()         
 | 
				
			||||||
 | 
					            return result[0]
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    def update_username(self, user_id, username):
 | 
				
			||||||
 | 
					        """Обновляем статус username"""
 | 
				
			||||||
 | 
					        with self.connection:
 | 
				
			||||||
 | 
					            return self.cursor.execute(f"UPDATE users SET name = ? WHERE user_id = ?", (username, user_id))
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    def check_username(self, user_id) -> str:
 | 
				
			||||||
 | 
					        """Проверяем username юзера в базе"""
 | 
				
			||||||
 | 
					        with self.connection:
 | 
				
			||||||
 | 
					            result = self.cursor.execute('SELECT `name` FROM `users` WHERE `user_id` = ?', (user_id,)).fetchall()
 | 
				
			||||||
 | 
					            user_moder = result[0]
 | 
				
			||||||
 | 
					            return (user_moder[0])
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    def check_lastQuestion(self, user_id) -> str:
 | 
				
			||||||
 | 
					        """Проверяем last_question в базе"""
 | 
				
			||||||
 | 
					        with self.connection:
 | 
				
			||||||
 | 
					            result = self.cursor.execute('SELECT `last_question` FROM `users` WHERE `user_id` = ?', (user_id,)).fetchall()
 | 
				
			||||||
 | 
					            user_moder = result[0]
 | 
				
			||||||
 | 
					            return (user_moder[0])
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    def update_lastQuestion(self, user_id, timeload):
 | 
				
			||||||
 | 
					        """Обновляем статус timeload"""
 | 
				
			||||||
 | 
					        with self.connection:
 | 
				
			||||||
 | 
					            return self.cursor.execute(f"UPDATE users SET last_question = ? WHERE user_id = ?", (timeload, user_id))
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    def close(self):
 | 
				
			||||||
 | 
					        """Закрываем соединение с БД"""
 | 
				
			||||||
 | 
					        self.connection.close()
 | 
				
			||||||
							
								
								
									
										47
									
								
								app/database/loader_db.py
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										47
									
								
								app/database/loader_db.py
									
									
									
									
									
										Normal file
									
								
							@ -0,0 +1,47 @@
 | 
				
			|||||||
 | 
					import os
 | 
				
			||||||
 | 
					from app.database.create_database import create_db
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					def check_bd():
 | 
				
			||||||
 | 
					    print('-------------------')
 | 
				
			||||||
 | 
					    if os.path.exists("app/database/data/database.db"): 
 | 
				
			||||||
 | 
					        print('[База данных] "database" загружена')
 | 
				
			||||||
 | 
					    else: 
 | 
				
			||||||
 | 
					        print('[База данных] "database" отсутствует')
 | 
				
			||||||
 | 
					        print('[База данных] "database" создание....')
 | 
				
			||||||
 | 
					        if create_db() != 0:
 | 
				
			||||||
 | 
					            return print('[error] [База данных] "database" Ошибка создание')
 | 
				
			||||||
 | 
					            exit()
 | 
				
			||||||
 | 
					        print('[База данных] "database" создание завершено')
 | 
				
			||||||
 | 
					        print('[База данных] "database" загружена')
 | 
				
			||||||
 | 
					    #print('-------------------')
 | 
				
			||||||
 | 
					    return
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					def check_config_settings():
 | 
				
			||||||
 | 
					    from app.settings.config import TOKEN, CHANNEL_WHITELIST
 | 
				
			||||||
 | 
					    error = False
 | 
				
			||||||
 | 
					    answer = '[config] Отсутствуют настройки (app/settings/config.py):'
 | 
				
			||||||
 | 
					    if (TOKEN == ""):
 | 
				
			||||||
 | 
					        error = True
 | 
				
			||||||
 | 
					        answer +='\nотсутствует TOKEN'
 | 
				
			||||||
 | 
					    if (CHANNEL_WHITELIST == "-100"):
 | 
				
			||||||
 | 
					        error = True
 | 
				
			||||||
 | 
					        answer +='\nотсутствует CHANNEL_WHITELIST'
 | 
				
			||||||
 | 
					    if error:
 | 
				
			||||||
 | 
					        print(answer)
 | 
				
			||||||
 | 
					        return False
 | 
				
			||||||
 | 
					    return True
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					def check_config():
 | 
				
			||||||
 | 
					    #print('-------------------')
 | 
				
			||||||
 | 
					    if os.path.exists("app/database/data/database.db"):
 | 
				
			||||||
 | 
					        if check_config_settings() != True:
 | 
				
			||||||
 | 
					            print('-------------------')
 | 
				
			||||||
 | 
					            exit()
 | 
				
			||||||
 | 
					        print('[config] "config" загружен')
 | 
				
			||||||
 | 
					        print('-------------------')
 | 
				
			||||||
 | 
					    else: 
 | 
				
			||||||
 | 
					        print('[config] "config" отсутствует')
 | 
				
			||||||
 | 
					        print('[config] используйте install или создайте app/settings/config.py по примеру app/settings/config_example.py')
 | 
				
			||||||
 | 
					        print('-------------------')
 | 
				
			||||||
 | 
					        exit()
 | 
				
			||||||
 | 
					    return
 | 
				
			||||||
							
								
								
									
										172
									
								
								app/engine.py
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										172
									
								
								app/engine.py
									
									
									
									
									
										Normal file
									
								
							@ -0,0 +1,172 @@
 | 
				
			|||||||
 | 
					import os
 | 
				
			||||||
 | 
					import re
 | 
				
			||||||
 | 
					from app.settings.config import DEBUG
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					class SearchEngine:
 | 
				
			||||||
 | 
					    def __init__(self, debug=False):
 | 
				
			||||||
 | 
					        self.debug = DEBUG  # Параметр для включения/выключения отладочного режима
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					        # Список необходимых папок
 | 
				
			||||||
 | 
					        self.required_folders = [
 | 
				
			||||||
 | 
					            "3D сканы",
 | 
				
			||||||
 | 
					            "Анализы",
 | 
				
			||||||
 | 
					            "Документы",
 | 
				
			||||||
 | 
					            "План лечения",
 | 
				
			||||||
 | 
					            "Снимки и КТ",
 | 
				
			||||||
 | 
					            "Фотографии"
 | 
				
			||||||
 | 
					        ]
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    # Метод для поиска в папке
 | 
				
			||||||
 | 
					    def search_folder(self, path, message_text):
 | 
				
			||||||
 | 
					        if self.debug:
 | 
				
			||||||
 | 
					            print("Searching folder")
 | 
				
			||||||
 | 
					            print("Path:", path)
 | 
				
			||||||
 | 
					            print("Message Text:", message_text)
 | 
				
			||||||
 | 
					        
 | 
				
			||||||
 | 
					        results = []  # Список для хранения результатов поиска
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					        # Проверка существования пути
 | 
				
			||||||
 | 
					        if not os.path.exists(path):
 | 
				
			||||||
 | 
					            print(f"Path '{path}' does not exist.")
 | 
				
			||||||
 | 
					            return results
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					        # Рекурсивный обход папок
 | 
				
			||||||
 | 
					        for root, dirs, files in os.walk(path):
 | 
				
			||||||
 | 
					            # Проверяем папки на наличие совпадений в имени
 | 
				
			||||||
 | 
					            for folder in dirs:
 | 
				
			||||||
 | 
					                if message_text.lower() in folder.lower():
 | 
				
			||||||
 | 
					                    full_path = os.path.join(root, folder)
 | 
				
			||||||
 | 
					                    results.append(full_path)
 | 
				
			||||||
 | 
					                    if self.debug:
 | 
				
			||||||
 | 
					                        print(f"Folder matched: {full_path}")
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					            # Проверяем файлы на наличие совпадений в имени
 | 
				
			||||||
 | 
					            for file in files:
 | 
				
			||||||
 | 
					                if message_text.lower() in file.lower():
 | 
				
			||||||
 | 
					                    full_path = os.path.join(root, file)
 | 
				
			||||||
 | 
					                    results.append(full_path)
 | 
				
			||||||
 | 
					                    if self.debug:
 | 
				
			||||||
 | 
					                        print(f"File matched: {full_path}")
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					        # Возвращаем список найденных совпадений
 | 
				
			||||||
 | 
					        return results
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    # Метод для точного поиска только в папках корневого уровня
 | 
				
			||||||
 | 
					    def search_exact_match(self, path, exact_name):
 | 
				
			||||||
 | 
					        if self.debug:
 | 
				
			||||||
 | 
					            print("Searching for exact match in root folder only")
 | 
				
			||||||
 | 
					            print("Path:", path)
 | 
				
			||||||
 | 
					            print("Exact Name:", exact_name)
 | 
				
			||||||
 | 
					            print("Type of exact_name:", type(exact_name))
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					        results = []  # Список для хранения результатов точного поиска
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					        # Преобразуем exact_name в строку, если это целое число
 | 
				
			||||||
 | 
					        if isinstance(exact_name, int):
 | 
				
			||||||
 | 
					            exact_name = str(exact_name)
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					        # Проверка существования пути
 | 
				
			||||||
 | 
					        if not os.path.exists(path):
 | 
				
			||||||
 | 
					            if self.debug:
 | 
				
			||||||
 | 
					                print(f"Path '{path}' does not exist.")
 | 
				
			||||||
 | 
					            return results
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					        # Проверка только корневых папок
 | 
				
			||||||
 | 
					        with os.scandir(path) as entries:
 | 
				
			||||||
 | 
					            for entry in entries:
 | 
				
			||||||
 | 
					                if entry.is_dir() and entry.name == exact_name:  # Только папки с точным совпадением
 | 
				
			||||||
 | 
					                    full_path = os.path.join(path, entry.name)
 | 
				
			||||||
 | 
					                    results.append(full_path)
 | 
				
			||||||
 | 
					                    if self.debug:
 | 
				
			||||||
 | 
					                        print(f"Folder matched (exact in root): {full_path}")
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					        return results
 | 
				
			||||||
 | 
					    
 | 
				
			||||||
 | 
					    # Метод для поиска файла с именем, соответствующим паттерну Фамилия_Имя, в папке пациента
 | 
				
			||||||
 | 
					    def find_patient_file(self, path, patient_id):
 | 
				
			||||||
 | 
					        if self.debug:
 | 
				
			||||||
 | 
					            print("Searching for patient file in folder")
 | 
				
			||||||
 | 
					            print("Root Path:", path)
 | 
				
			||||||
 | 
					            print("Patient ID:", patient_id)
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					        # Полный путь к папке пациента
 | 
				
			||||||
 | 
					        patient_folder_path = os.path.join(path, str(patient_id))
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					        # Проверка, существует ли указанная папка пациента
 | 
				
			||||||
 | 
					        if not os.path.exists(patient_folder_path) or not os.path.isdir(patient_folder_path):
 | 
				
			||||||
 | 
					            if self.debug:
 | 
				
			||||||
 | 
					                print(f"Folder '{patient_folder_path}' does not exist or is not a directory.")
 | 
				
			||||||
 | 
					            return None
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					        # Паттерн для поиска файла с форматом Фамилия_Имя
 | 
				
			||||||
 | 
					        pattern = re.compile(r"^[А-Яа-яЁёA-Za-z]+_[А-Яа-яЁёA-Za-z]+")
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					        # Поиск файла, соответствующего паттерну, в папке пациента
 | 
				
			||||||
 | 
					        with os.scandir(patient_folder_path) as entries:
 | 
				
			||||||
 | 
					            for entry in entries:
 | 
				
			||||||
 | 
					                if entry.is_file() and pattern.match(entry.name):
 | 
				
			||||||
 | 
					                    full_path = os.path.join(patient_folder_path, entry.name)
 | 
				
			||||||
 | 
					                    if self.debug:
 | 
				
			||||||
 | 
					                        print(f"File matched: {full_path}")
 | 
				
			||||||
 | 
					                        print(f"entry.name: {entry.name}")
 | 
				
			||||||
 | 
					                    return entry.name
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					        # Если файл не найден, возвращаем None
 | 
				
			||||||
 | 
					        if self.debug:
 | 
				
			||||||
 | 
					            print(f"No matching file found in folder '{patient_folder_path}'.")
 | 
				
			||||||
 | 
					        return None
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    def check_and_create_patient_folders(self, path, patient_id):
 | 
				
			||||||
 | 
					        # Полный путь к папке пациента
 | 
				
			||||||
 | 
					        patient_folder_path = os.path.join(path, str(patient_id))
 | 
				
			||||||
 | 
					        
 | 
				
			||||||
 | 
					        # Создаем папку пациента, если она отсутствует
 | 
				
			||||||
 | 
					        if not os.path.exists(patient_folder_path):
 | 
				
			||||||
 | 
					            os.makedirs(patient_folder_path)
 | 
				
			||||||
 | 
					            if self.debug:
 | 
				
			||||||
 | 
					                print(f"Created patient folder: {patient_folder_path}")
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					        # Проверка каждой требуемой папки
 | 
				
			||||||
 | 
					        for folder_name in self.required_folders:
 | 
				
			||||||
 | 
					            full_folder_path = os.path.join(patient_folder_path, folder_name)
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					            # Если папка не существует, создаем её
 | 
				
			||||||
 | 
					            if not os.path.exists(full_folder_path):
 | 
				
			||||||
 | 
					                os.makedirs(full_folder_path)
 | 
				
			||||||
 | 
					                if self.debug:
 | 
				
			||||||
 | 
					                    print(f"Created missing folder: {full_folder_path}")
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					        # Возвращаем список всех папок пациента
 | 
				
			||||||
 | 
					        folder_list = []
 | 
				
			||||||
 | 
					        for folder_name in self.required_folders:
 | 
				
			||||||
 | 
					            folder_list.append(folder_name)
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					        return folder_list
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    # Метод для поиска всех файлов в заданной папке
 | 
				
			||||||
 | 
					    def find_user_files(self, base_path, patient_id, folder_name, username):
 | 
				
			||||||
 | 
					        if self.debug:
 | 
				
			||||||
 | 
					            print("Searching for files in folder")
 | 
				
			||||||
 | 
					            print("Base Path:", base_path)
 | 
				
			||||||
 | 
					            print("Patient ID:", patient_id)
 | 
				
			||||||
 | 
					            print("Folder Name:", folder_name)
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					        # Путь к папке пользователя
 | 
				
			||||||
 | 
					        folder_path = os.path.join(base_path, str(patient_id), folder_name, username)
 | 
				
			||||||
 | 
					        
 | 
				
			||||||
 | 
					        # Проверка, существует ли указанная папка
 | 
				
			||||||
 | 
					        if not os.path.exists(folder_path):
 | 
				
			||||||
 | 
					            if self.debug:
 | 
				
			||||||
 | 
					                print(f"Folder '{folder_path}' does not exist.")
 | 
				
			||||||
 | 
					            return []
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					        # Получаем список файлов в папке
 | 
				
			||||||
 | 
					        files = []
 | 
				
			||||||
 | 
					        with os.scandir(folder_path) as entries:
 | 
				
			||||||
 | 
					            for entry in entries:
 | 
				
			||||||
 | 
					                if entry.is_file():
 | 
				
			||||||
 | 
					                    files.append(entry.name)
 | 
				
			||||||
 | 
					                    if self.debug:
 | 
				
			||||||
 | 
					                        print(f"Found file: {entry.name}")
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					        return files
 | 
				
			||||||
							
								
								
									
										177
									
								
								app/install.py
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										177
									
								
								app/install.py
									
									
									
									
									
										Normal file
									
								
							@ -0,0 +1,177 @@
 | 
				
			|||||||
 | 
					import os
 | 
				
			||||||
 | 
					import platform
 | 
				
			||||||
 | 
					import sys
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					python_version = (3, 12)
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					def clear_console():
 | 
				
			||||||
 | 
					    os_name = platform.system()
 | 
				
			||||||
 | 
					    if os_name == 'Windows':
 | 
				
			||||||
 | 
					        os.system('cls')
 | 
				
			||||||
 | 
					    else:
 | 
				
			||||||
 | 
					        os.system('clear')
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					def run_command(command):
 | 
				
			||||||
 | 
					    result = os.system(command)
 | 
				
			||||||
 | 
					    if result == 0:
 | 
				
			||||||
 | 
					        return True
 | 
				
			||||||
 | 
					    else:
 | 
				
			||||||
 | 
					        print(f"Command failed with status code {result}")
 | 
				
			||||||
 | 
					        return False
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					def check_python_version():
 | 
				
			||||||
 | 
					    current_version = sys.version_info
 | 
				
			||||||
 | 
					    required_version = python_version
 | 
				
			||||||
 | 
					    if current_version < required_version:
 | 
				
			||||||
 | 
					        print(f"Python version {required_version[0]}.{required_version[1]} or newer is required.")
 | 
				
			||||||
 | 
					        return False
 | 
				
			||||||
 | 
					    return True
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					class configuration:
 | 
				
			||||||
 | 
					    
 | 
				
			||||||
 | 
					    def __init__(self):
 | 
				
			||||||
 | 
					        clear_console()
 | 
				
			||||||
 | 
					        self.config_path = "app/settings/config.py"  # Путь к файлу конфигурации
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    def check_config(self):
 | 
				
			||||||
 | 
					        if not os.path.exists(self.config_path):
 | 
				
			||||||
 | 
					            #print("[2/2] Config not found.")
 | 
				
			||||||
 | 
					            return False
 | 
				
			||||||
 | 
					        else:
 | 
				
			||||||
 | 
					            #print("[2/2] Config exists.")
 | 
				
			||||||
 | 
					            return True
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    def ask_to_recreate_config(self):
 | 
				
			||||||
 | 
					        user_input = input("[2/2] Config already exists. Do you want to delete it and reinstall? (y/n): ").strip().lower()
 | 
				
			||||||
 | 
					        
 | 
				
			||||||
 | 
					        if user_input == 'y':
 | 
				
			||||||
 | 
					            print("[2/2] Deleting the config.py...")
 | 
				
			||||||
 | 
					            self.delete_config()
 | 
				
			||||||
 | 
					            if self.check_config():
 | 
				
			||||||
 | 
					                self.ask_to_recreate_config()  # Повторный запрос
 | 
				
			||||||
 | 
					            self.create_config()
 | 
				
			||||||
 | 
					        elif user_input == 'n':
 | 
				
			||||||
 | 
					            print("[2/2] Skipping the recreation of config.")
 | 
				
			||||||
 | 
					        else:
 | 
				
			||||||
 | 
					            print("[2/2] Invalid input. Please answer with 'y' or 'n'.")
 | 
				
			||||||
 | 
					            self.ask_to_recreate_config()  # Повторный запрос
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    def delete_config(self):
 | 
				
			||||||
 | 
					        try:
 | 
				
			||||||
 | 
					            if os.path.exists(self.config_path):
 | 
				
			||||||
 | 
					                os.remove(self.config_path)
 | 
				
			||||||
 | 
					                print("[2/2] The config has been deleted.")
 | 
				
			||||||
 | 
					            else:
 | 
				
			||||||
 | 
					                print("[2/2] Config file not found; nothing to delete.")
 | 
				
			||||||
 | 
					        except Exception as e:
 | 
				
			||||||
 | 
					            print(f"[2/2] Error while deleting config: {e}")
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    def create_config(self):
 | 
				
			||||||
 | 
					        token = input("[2/2] Enter your telegram bot token: ").strip()
 | 
				
			||||||
 | 
					        channel_id = input("[2/2] Enter your channel_id: ").strip()
 | 
				
			||||||
 | 
					        path = input("[2/2] Enter your path: ").strip()
 | 
				
			||||||
 | 
					        
 | 
				
			||||||
 | 
					        try:
 | 
				
			||||||
 | 
					            os.makedirs(os.path.dirname(self.config_path), exist_ok=True)
 | 
				
			||||||
 | 
					            with open(self.config_path, "w") as config_file:
 | 
				
			||||||
 | 
					                #config_file.write(f'TOKEN = "{token}"\n')
 | 
				
			||||||
 | 
					                config_file.write(f'DEBUG = False\nTOKEN = "{token}"\nCHANNEL_WHITELIST = "-100{channel_id}"\n')
 | 
				
			||||||
 | 
					            print("----------------------------------------------------------------")
 | 
				
			||||||
 | 
					            print("[2/2] Config creation succeeded")
 | 
				
			||||||
 | 
					            print("----------------------------------------------------------------")
 | 
				
			||||||
 | 
					        except Exception as e:
 | 
				
			||||||
 | 
					            print(f"[2/2] Error while creating config: {e}")
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    def start(self):
 | 
				
			||||||
 | 
					        if self.check_config():
 | 
				
			||||||
 | 
					            self.ask_to_recreate_config()
 | 
				
			||||||
 | 
					        else:
 | 
				
			||||||
 | 
					            self.create_config()
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					class installation:
 | 
				
			||||||
 | 
					    
 | 
				
			||||||
 | 
					    def __init__(self):
 | 
				
			||||||
 | 
					        clear_console()
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    def check_env_folder(self):
 | 
				
			||||||
 | 
					        """Проверка наличия папки 'env'. Если её нет - предложим создать."""
 | 
				
			||||||
 | 
					        if not os.path.exists("env"):
 | 
				
			||||||
 | 
					            print("[1/2] installing environment...")
 | 
				
			||||||
 | 
					            return False
 | 
				
			||||||
 | 
					        else:
 | 
				
			||||||
 | 
					            # print("[1/2] Folder 'env' exists.")
 | 
				
			||||||
 | 
					            return True
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    def ask_to_recreate_env(self):
 | 
				
			||||||
 | 
					        """Запросить у пользователя, хочет ли он удалить старую среду и создать новую."""
 | 
				
			||||||
 | 
					        user_input = input("[1/2] Folder 'env' already exists. Do you want to delete it and reinstall? (y/n): ").strip().lower()
 | 
				
			||||||
 | 
					        
 | 
				
			||||||
 | 
					        if user_input == 'y':
 | 
				
			||||||
 | 
					            print("[1/2] Deleting the 'env' folder...")
 | 
				
			||||||
 | 
					            self.delete_env_folder()
 | 
				
			||||||
 | 
					            if self.check_env_folder():
 | 
				
			||||||
 | 
					                self.ask_to_recreate_env()  # Повторный запрос
 | 
				
			||||||
 | 
					            self.install_env()
 | 
				
			||||||
 | 
					        elif user_input == 'n':
 | 
				
			||||||
 | 
					            print("[1/2] Skipping the recreation of 'env'.")
 | 
				
			||||||
 | 
					        else:
 | 
				
			||||||
 | 
					            print("[1/2] Invalid input. Please answer with 'y' or 'n'.")
 | 
				
			||||||
 | 
					            self.ask_to_recreate_env()  # Повторный запрос
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    def delete_env_folder(self):
 | 
				
			||||||
 | 
					        """Удаление папки 'env'."""
 | 
				
			||||||
 | 
					        if os.path.exists("env"):
 | 
				
			||||||
 | 
					            try:
 | 
				
			||||||
 | 
					                # Удаляем всю папку 'env' рекурсивно
 | 
				
			||||||
 | 
					                import shutil
 | 
				
			||||||
 | 
					                shutil.rmtree("env")
 | 
				
			||||||
 | 
					                print("[1/2] The 'env' folder has been deleted.")
 | 
				
			||||||
 | 
					            except Exception as e:
 | 
				
			||||||
 | 
					                print(f"[1/2] Error while deleting 'env': {e}")
 | 
				
			||||||
 | 
					        else:
 | 
				
			||||||
 | 
					            print("[1/2] Folder 'env' does not exist. No need to delete.")
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    def create_env(self):
 | 
				
			||||||
 | 
					        os_name = platform.system()
 | 
				
			||||||
 | 
					        if os_name != 'Windows':
 | 
				
			||||||
 | 
					            #
 | 
				
			||||||
 | 
					            print("[!!!] CRITICAL WARNING")
 | 
				
			||||||
 | 
					            print("[!!!] install for not windows not working")
 | 
				
			||||||
 | 
					            print("[!!!] use user manual")
 | 
				
			||||||
 | 
					            choice = input('Wait any key...')
 | 
				
			||||||
 | 
					            # run_command("python3 -m venv env")
 | 
				
			||||||
 | 
					            # run_command("./env/bin/pip install -r requirements.txt")
 | 
				
			||||||
 | 
					        run_command("python -m venv env")
 | 
				
			||||||
 | 
					        run_command(".\\env\\Scripts\\pip.exe install -r requirements.txt")
 | 
				
			||||||
 | 
					        # clear_console()
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    def install_env(self):
 | 
				
			||||||
 | 
					        installation_s = installation()
 | 
				
			||||||
 | 
					        if installation_s.check_env_folder() == False:
 | 
				
			||||||
 | 
					            installation_s.create_env()
 | 
				
			||||||
 | 
					            clear_console()
 | 
				
			||||||
 | 
					            print("----------------------------------------------------------------")
 | 
				
			||||||
 | 
					            print("[1/2] Installation succeeded")
 | 
				
			||||||
 | 
					            print("----------------------------------------------------------------")
 | 
				
			||||||
 | 
					            choice = input('Wait any key...')
 | 
				
			||||||
 | 
					        else:
 | 
				
			||||||
 | 
					            installation_s.ask_to_recreate_env()
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    def start(self):
 | 
				
			||||||
 | 
					        if not check_python_version():
 | 
				
			||||||
 | 
					            return
 | 
				
			||||||
 | 
					        self.install_env()
 | 
				
			||||||
 | 
					        # print("[1/2] Installation completed successfully")
 | 
				
			||||||
 | 
					        # choice = input('Wait any key...')
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					if __name__ == "__main__":
 | 
				
			||||||
 | 
					    install = installation()
 | 
				
			||||||
 | 
					    install.start()
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    config = configuration()
 | 
				
			||||||
 | 
					    config.start()
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    print("Installation completed successfully")
 | 
				
			||||||
 | 
					    choice = input('Wait any key...')
 | 
				
			||||||
							
								
								
									
										130
									
								
								app/keyboards.py
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										130
									
								
								app/keyboards.py
									
									
									
									
									
										Normal file
									
								
							@ -0,0 +1,130 @@
 | 
				
			|||||||
 | 
					from aiogram import types
 | 
				
			||||||
 | 
					from aiogram.types import Message, ReplyKeyboardRemove
 | 
				
			||||||
 | 
					from aiogram.filters.callback_data import CallbackData
 | 
				
			||||||
 | 
					from app.messages import INFO_MESSAGES
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					#----------------------------------------
 | 
				
			||||||
 | 
					closekeyboards = types.ReplyKeyboardRemove()
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					button_cancel = [
 | 
				
			||||||
 | 
					    [types.KeyboardButton(text="Отмена"),],
 | 
				
			||||||
 | 
					]
 | 
				
			||||||
 | 
					cancel = types.ReplyKeyboardMarkup(
 | 
				
			||||||
 | 
					    keyboard=button_cancel,
 | 
				
			||||||
 | 
					    resize_keyboard=True,
 | 
				
			||||||
 | 
					)
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					da_1 = [
 | 
				
			||||||
 | 
					    [types.KeyboardButton(text="Отмена"),],
 | 
				
			||||||
 | 
					    [types.KeyboardButton(text="Да"),],
 | 
				
			||||||
 | 
					]
 | 
				
			||||||
 | 
					da = types.ReplyKeyboardMarkup(
 | 
				
			||||||
 | 
					    keyboard=da_1,
 | 
				
			||||||
 | 
					    resize_keyboard=True,
 | 
				
			||||||
 | 
					)
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					spam_1 = [
 | 
				
			||||||
 | 
					    [types.KeyboardButton(text="Отмена"),],
 | 
				
			||||||
 | 
					    [types.KeyboardButton(text="Всем"),],
 | 
				
			||||||
 | 
					    [types.KeyboardButton(text="С доступом"),],
 | 
				
			||||||
 | 
					]
 | 
				
			||||||
 | 
					spam = types.ReplyKeyboardMarkup(
 | 
				
			||||||
 | 
					    keyboard=spam_1,
 | 
				
			||||||
 | 
					    resize_keyboard=True,
 | 
				
			||||||
 | 
					)
 | 
				
			||||||
 | 
					#----------------------------------------
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					# main menu
 | 
				
			||||||
 | 
					#----------------------------------------
 | 
				
			||||||
 | 
					button_menu = [
 | 
				
			||||||
 | 
					    [types.KeyboardButton(text="📚 Студентам")],
 | 
				
			||||||
 | 
					    [types.KeyboardButton(text="🤝 Работодателям")],
 | 
				
			||||||
 | 
					    [types.KeyboardButton(text="ℹ️ О центре")],
 | 
				
			||||||
 | 
					    #[types.KeyboardButton(text="📰 Подписка на новости")],
 | 
				
			||||||
 | 
					]
 | 
				
			||||||
 | 
					main_menu = types.ReplyKeyboardMarkup(
 | 
				
			||||||
 | 
					    keyboard=button_menu,
 | 
				
			||||||
 | 
					    resize_keyboard=True,
 | 
				
			||||||
 | 
					)
 | 
				
			||||||
 | 
					#----------------------------------------
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					# menu_1
 | 
				
			||||||
 | 
					#----------------------------------------
 | 
				
			||||||
 | 
					button_menu_1 = [
 | 
				
			||||||
 | 
					    [types.KeyboardButton(text="📖 Стажировки, практики и вакансии")],
 | 
				
			||||||
 | 
					    [types.KeyboardButton(text="✍️ Советы по резюме")],
 | 
				
			||||||
 | 
					    [types.KeyboardButton(text="📄 Оформление договора")],
 | 
				
			||||||
 | 
					    [types.KeyboardButton(text="🏠 Главная")],
 | 
				
			||||||
 | 
					]
 | 
				
			||||||
 | 
					menu_1 = types.ReplyKeyboardMarkup(
 | 
				
			||||||
 | 
					    keyboard=button_menu_1,
 | 
				
			||||||
 | 
					    resize_keyboard=True,
 | 
				
			||||||
 | 
					)
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					button_menu_1_1 = [
 | 
				
			||||||
 | 
					    [types.KeyboardButton(text="📚 Стажировки")],
 | 
				
			||||||
 | 
					    [types.KeyboardButton(text="🛠 Практики")],
 | 
				
			||||||
 | 
					    [types.KeyboardButton(text="💼 Вакансии")],
 | 
				
			||||||
 | 
					    [types.KeyboardButton(text="🔙 Назад")],
 | 
				
			||||||
 | 
					]
 | 
				
			||||||
 | 
					menu_1_1 = types.ReplyKeyboardMarkup(
 | 
				
			||||||
 | 
					    keyboard=button_menu_1_1,
 | 
				
			||||||
 | 
					    resize_keyboard=True,
 | 
				
			||||||
 | 
					)
 | 
				
			||||||
 | 
					#----------------------------------------
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					# main menu inline
 | 
				
			||||||
 | 
					#----------------------------------------
 | 
				
			||||||
 | 
					menu_1_1_1_inline_add = [
 | 
				
			||||||
 | 
					    [types.InlineKeyboardButton(text="Узнать о стажировках", url=INFO_MESSAGES['link_menu_1_1_1'])],
 | 
				
			||||||
 | 
					]
 | 
				
			||||||
 | 
					menu_1_1_1_inline = types.InlineKeyboardMarkup(inline_keyboard=menu_1_1_1_inline_add)
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					menu_1_1_2_inline_add = [
 | 
				
			||||||
 | 
					    [types.InlineKeyboardButton(text=" Подробнее о практиках", url=INFO_MESSAGES['link_menu_1_1_2'])],
 | 
				
			||||||
 | 
					]
 | 
				
			||||||
 | 
					menu_1_1_2_inline = types.InlineKeyboardMarkup(inline_keyboard=menu_1_1_2_inline_add)
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					menu_1_1_3_inline_add = [
 | 
				
			||||||
 | 
					    [types.InlineKeyboardButton(text="Перейти в Telegram-канал с вакансиями", url=INFO_MESSAGES['link_menu_1_1_3'])],
 | 
				
			||||||
 | 
					]
 | 
				
			||||||
 | 
					menu_1_1_3_inline = types.InlineKeyboardMarkup(inline_keyboard=menu_1_1_3_inline_add)
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					menu_1_2_inline_add = [
 | 
				
			||||||
 | 
					    [types.InlineKeyboardButton(text="Перейти к советам по резюме", url=INFO_MESSAGES['link_menu_1_2'])],
 | 
				
			||||||
 | 
					]
 | 
				
			||||||
 | 
					menu_1_2_inline = types.InlineKeyboardMarkup(inline_keyboard=menu_1_2_inline_add)
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					menu_1_3_inline_add = [
 | 
				
			||||||
 | 
					    [types.InlineKeyboardButton(text="Заполнить заявку", url=INFO_MESSAGES['link_menu_1_3'])],
 | 
				
			||||||
 | 
					]
 | 
				
			||||||
 | 
					menu_1_3_inline = types.InlineKeyboardMarkup(inline_keyboard=menu_1_3_inline_add)
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					menu_2_inline_add = [
 | 
				
			||||||
 | 
					    [types.InlineKeyboardButton(text="Виды сотрудничества с СПбГЭТУ ЛЭТИ", url=INFO_MESSAGES['link_rabotod'])],
 | 
				
			||||||
 | 
					]
 | 
				
			||||||
 | 
					menu_2_inline = types.InlineKeyboardMarkup(inline_keyboard=menu_2_inline_add)
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					menu_3_inline_add = [
 | 
				
			||||||
 | 
					    [types.InlineKeyboardButton(text="Подписаться на Telegram-канал", url=INFO_MESSAGES['public_telegram'])],
 | 
				
			||||||
 | 
					    [types.InlineKeyboardButton(text="Подписаться на группу ВКонтакте", url=INFO_MESSAGES['public_vk'])]
 | 
				
			||||||
 | 
					]
 | 
				
			||||||
 | 
					menu_3_inline = types.InlineKeyboardMarkup(inline_keyboard=menu_3_inline_add)
 | 
				
			||||||
 | 
					#----------------------------------------
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					# # main menu
 | 
				
			||||||
 | 
					# #----------------------------------------
 | 
				
			||||||
 | 
					# button_menu = [
 | 
				
			||||||
 | 
					#     [types.KeyboardButton(text="Информация о стажировках")],
 | 
				
			||||||
 | 
					#     [types.KeyboardButton(text="Информация о практиках")],
 | 
				
			||||||
 | 
					#     [types.KeyboardButton(text="Раздел вакансий")],
 | 
				
			||||||
 | 
					#     [types.KeyboardButton(text="Раздел для работодателей")],
 | 
				
			||||||
 | 
					#     [types.KeyboardButton(text="Советы по написанию резюме")],
 | 
				
			||||||
 | 
					# ]
 | 
				
			||||||
 | 
					# main_menu = types.ReplyKeyboardMarkup(
 | 
				
			||||||
 | 
					#     keyboard=button_menu,
 | 
				
			||||||
 | 
					#     resize_keyboard=True,
 | 
				
			||||||
 | 
					# )
 | 
				
			||||||
 | 
					# #----------------------------------------
 | 
				
			||||||
							
								
								
									
										70
									
								
								app/messages.py
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										70
									
								
								app/messages.py
									
									
									
									
									
										Normal file
									
								
							@ -0,0 +1,70 @@
 | 
				
			|||||||
 | 
					from app.settings.info import feedback_link
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					# messages
 | 
				
			||||||
 | 
					start_message = f'👋 Привет! Я чат-бот Центра развития карьеры СПбГЭТУ ЛЭТИ.\n\nПомогу тебе узнать о стажировках, практиках, вакансиях и многом другом!\n\nВыбери интересующий тебя раздел:'
 | 
				
			||||||
 | 
					error_message = f'⚠️ Ошибка сервера ⚠️\n\nFeedback: @{feedback_link}'
 | 
				
			||||||
 | 
					usestart_message = '🏠 Используй /start'
 | 
				
			||||||
 | 
					byebye_message = '✋ Я всегда рад помочь, обращайтесь.'
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					menu_1_message = 'Выберите интересующий вас раздел:'
 | 
				
			||||||
 | 
					menu_2_message = 'Если вы хотите разместить вакансию или сотрудничать с нашим университетом, ознакомьтесь с информацией здесь:'
 | 
				
			||||||
 | 
					menu_3_message = 'Подпишись на наши каналы, чтобы не пропустить важные новости и обновления:'
 | 
				
			||||||
 | 
					#menu_4_message = 'Подпишись на наши каналы, чтобы не пропустить важные новости и обновления:'
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					menu_1_1_1_message = 'Всё о стажировках:'
 | 
				
			||||||
 | 
					menu_1_1_2_message = 'Информация о практиках:'
 | 
				
			||||||
 | 
					menu_1_1_3_message = 'Все вакансии для студентов и выпускников:'
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					menu_1_1_message = 'Выберите, что вас интересует:'
 | 
				
			||||||
 | 
					menu_1_2_message = 'Подготовь своё резюме правильно! Советы и инструкции доступны здесь:'
 | 
				
			||||||
 | 
					menu_1_3_message = 'Для оформления договора на практику или стажировку воспользуйтесь этим инструментом:'
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					MESSAGES = {
 | 
				
			||||||
 | 
					    'start': start_message,
 | 
				
			||||||
 | 
					    'error': error_message,
 | 
				
			||||||
 | 
					    'usestart': usestart_message,
 | 
				
			||||||
 | 
					    'byebye': byebye_message,
 | 
				
			||||||
 | 
					    # menu
 | 
				
			||||||
 | 
					    'menu_1': menu_1_message,
 | 
				
			||||||
 | 
					    'menu_2': menu_2_message,
 | 
				
			||||||
 | 
					    'menu_3': menu_3_message,
 | 
				
			||||||
 | 
					   # 'menu_4': menu_4_message,
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    'menu_1_1_1': menu_1_1_1_message,
 | 
				
			||||||
 | 
					    'menu_1_1_2': menu_1_1_2_message,
 | 
				
			||||||
 | 
					    'menu_1_1_3': menu_1_1_3_message,
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    'menu_1_1': menu_1_1_message,
 | 
				
			||||||
 | 
					    'menu_1_2': menu_1_2_message,
 | 
				
			||||||
 | 
					    'menu_1_3': menu_1_3_message,
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					# info
 | 
				
			||||||
 | 
					# public_telegram_message = f'https://t.me/doctor_what'
 | 
				
			||||||
 | 
					# public_vk_message = f'https://t.me/doctor_what'
 | 
				
			||||||
 | 
					# link_rabotod_message = f'https://t.me/doctor_what' # (🤝 Работодателям)
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					# link_menu_1_1_1_message = f'https://t.me/doctor_what' # (📚 Стажировки)
 | 
				
			||||||
 | 
					# link_menu_1_1_2_message = f'https://t.me/doctor_what' # (🛠 Практики)
 | 
				
			||||||
 | 
					# link_menu_1_1_3_message = f'https://t.me/doctor_what' # (💼 Вакансии)
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					# link_menu_1_2_message = f'https://t.me/doctor_what' # (✍️ Советы по резюме)
 | 
				
			||||||
 | 
					# link_menu_1_3_message = f'https://t.me/doctor_what' # (📄 Оформление договора)
 | 
				
			||||||
 | 
					from app.settings.info import public_telegram_message, public_vk_message, link_rabotod_message, \
 | 
				
			||||||
 | 
					    link_menu_1_1_1_message, link_menu_1_1_2_message, link_menu_1_1_3_message, \
 | 
				
			||||||
 | 
					    link_menu_1_2_message, link_menu_1_3_message
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					INFO_MESSAGES = {
 | 
				
			||||||
 | 
					    'public_telegram': public_telegram_message,
 | 
				
			||||||
 | 
					    'public_vk': public_vk_message,
 | 
				
			||||||
 | 
					    'link_rabotod': link_rabotod_message,
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    'link_menu_1_1_1': link_menu_1_1_1_message,
 | 
				
			||||||
 | 
					    'link_menu_1_1_2': link_menu_1_1_2_message,
 | 
				
			||||||
 | 
					    'link_menu_1_1_3': link_menu_1_1_3_message,
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    'link_menu_1_2': link_menu_1_2_message,
 | 
				
			||||||
 | 
					    'link_menu_1_3': link_menu_1_3_message,
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
							
								
								
									
										3
									
								
								app/settings/config example.py
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										3
									
								
								app/settings/config example.py
									
									
									
									
									
										Normal file
									
								
							@ -0,0 +1,3 @@
 | 
				
			|||||||
 | 
					DEBUG = False
 | 
				
			||||||
 | 
					TOKEN = "" # bot token
 | 
				
			||||||
 | 
					CHANNEL_WHITELIST = "" # -100+channel_id (-100474747474747474747474747)
 | 
				
			||||||
							
								
								
									
										15
									
								
								app/settings/info.py
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										15
									
								
								app/settings/info.py
									
									
									
									
									
										Normal file
									
								
							@ -0,0 +1,15 @@
 | 
				
			|||||||
 | 
					# ни на что не влияет, только кастомизация сообщений
 | 
				
			||||||
 | 
					bot_link = 'test_BOT'
 | 
				
			||||||
 | 
					feedback_link = 'test_FeedBack_Bot'
 | 
				
			||||||
 | 
					public_link = 'test_Public'
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					public_telegram_message = 'https://publictelegrammessage.ru'
 | 
				
			||||||
 | 
					public_vk_message = 'https://publicvkmessage.ru'
 | 
				
			||||||
 | 
					link_rabotod_message = 'https://linkrabotodmessage.ru' # (🤝 Работодателям)
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					link_menu_1_1_1_message = 'https://linkmenu111message.ru' # (📚 Стажировки)
 | 
				
			||||||
 | 
					link_menu_1_1_2_message = 'https://linkmenu112message.ru' # (🛠 Практики)
 | 
				
			||||||
 | 
					link_menu_1_1_3_message = 'https://linkmenu113message.ru' # (💼 Вакансии)
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					link_menu_1_2_message = 'https://linkmenu12message.ru' # (✍️ Советы по резюме)
 | 
				
			||||||
 | 
					link_menu_1_3_message = 'https://linkmenu13message.ru' # (📄 Оформление договора)
 | 
				
			||||||
							
								
								
									
										5
									
								
								autostart/telegram_bot.bat
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										5
									
								
								autostart/telegram_bot.bat
									
									
									
									
									
										Normal file
									
								
							@ -0,0 +1,5 @@
 | 
				
			|||||||
 | 
					@echo off
 | 
				
			||||||
 | 
					REM скрипт автозапуска. Win + R, shell:startup Скопируйте туда этот BAT-файл.
 | 
				
			||||||
 | 
					cd /d G:\your_location\telegram_bot_stomplan
 | 
				
			||||||
 | 
					.\env\Scripts\python server.py
 | 
				
			||||||
 | 
					pause
 | 
				
			||||||
							
								
								
									
										4
									
								
								autostart/telegram_bot_hidden.bat
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										4
									
								
								autostart/telegram_bot_hidden.bat
									
									
									
									
									
										Normal file
									
								
							@ -0,0 +1,4 @@
 | 
				
			|||||||
 | 
					@echo off
 | 
				
			||||||
 | 
					REM скрипт автозапуска hidden. Win + R, shell:startup Скопируйте туда этот BAT-файл.
 | 
				
			||||||
 | 
					cd /d G:\your_location\telegram_bot_stomplan
 | 
				
			||||||
 | 
					.\env\Scripts\pythonw.exe server.py
 | 
				
			||||||
							
								
								
									
										4
									
								
								install.bat
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										4
									
								
								install.bat
									
									
									
									
									
										Normal file
									
								
							@ -0,0 +1,4 @@
 | 
				
			|||||||
 | 
					@echo off
 | 
				
			||||||
 | 
					REM
 | 
				
			||||||
 | 
					python app/install.py
 | 
				
			||||||
 | 
					pause
 | 
				
			||||||
							
								
								
									
										1
									
								
								requirements.txt
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										1
									
								
								requirements.txt
									
									
									
									
									
										Normal file
									
								
							@ -0,0 +1 @@
 | 
				
			|||||||
 | 
					aiogram==3.15
 | 
				
			||||||
							
								
								
									
										224
									
								
								server.py
									
									
									
									
									
										Normal file
									
								
							
							
						
						
									
										224
									
								
								server.py
									
									
									
									
									
										Normal file
									
								
							@ -0,0 +1,224 @@
 | 
				
			|||||||
 | 
					import asyncio
 | 
				
			||||||
 | 
					import os
 | 
				
			||||||
 | 
					from datetime import datetime
 | 
				
			||||||
 | 
					import time
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					from aiogram import Bot, Dispatcher, F, Router, types
 | 
				
			||||||
 | 
					from aiogram.fsm.context import FSMContext
 | 
				
			||||||
 | 
					from aiogram.fsm.state import State, StatesGroup
 | 
				
			||||||
 | 
					from aiogram.fsm.storage.memory import MemoryStorage
 | 
				
			||||||
 | 
					from aiogram.filters import Command, StateFilter
 | 
				
			||||||
 | 
					from aiogram.types import Message
 | 
				
			||||||
 | 
					from aiogram.utils.keyboard import InlineKeyboardBuilder
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					import app.keyboards as kb
 | 
				
			||||||
 | 
					from app.messages import MESSAGES
 | 
				
			||||||
 | 
					from app.settings.config import DEBUG, TOKEN, CHANNEL_WHITELIST
 | 
				
			||||||
 | 
					from app.settings.info import bot_link
 | 
				
			||||||
 | 
					from app.database.loader_db import check_bd, check_config
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					#запуск
 | 
				
			||||||
 | 
					#----------------------------------------
 | 
				
			||||||
 | 
					check_bd()
 | 
				
			||||||
 | 
					check_config()
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					dp = Dispatcher(storage=MemoryStorage())
 | 
				
			||||||
 | 
					bot = Bot(token=TOKEN)
 | 
				
			||||||
 | 
					router = Router()
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					from app.database.db_connector import ALLusers
 | 
				
			||||||
 | 
					checkuser = ALLusers('app/database/data/database.db')
 | 
				
			||||||
 | 
					available_da = ["Да"]
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					async def main():
 | 
				
			||||||
 | 
					    if DEBUG: print('DEBUG mode')
 | 
				
			||||||
 | 
					    print(f'Bot start @{bot_link}')
 | 
				
			||||||
 | 
					    await bot.delete_webhook(drop_pending_updates=True)
 | 
				
			||||||
 | 
					    await dp.start_polling(bot)
 | 
				
			||||||
 | 
					#----------------------------------------
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					# access
 | 
				
			||||||
 | 
					#----------------------------------------
 | 
				
			||||||
 | 
					async def check_admin(message_chat_id):
 | 
				
			||||||
 | 
					    try:
 | 
				
			||||||
 | 
					        channel_id = CHANNEL_WHITELIST
 | 
				
			||||||
 | 
					        user_channel_status = await bot.get_chat_member(chat_id=channel_id, user_id=message_chat_id)
 | 
				
			||||||
 | 
					        if DEBUG:
 | 
				
			||||||
 | 
					            print('---------------------------------------')
 | 
				
			||||||
 | 
					            print('user_channel_status', user_channel_status.status)
 | 
				
			||||||
 | 
					            print('---------------------------------------')
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					        if ((user_channel_status.status == 'creator') or (user_channel_status.status == 'administrator')):
 | 
				
			||||||
 | 
					            if DEBUG:
 | 
				
			||||||
 | 
					                print('Admin access')
 | 
				
			||||||
 | 
					            return True
 | 
				
			||||||
 | 
					        return False
 | 
				
			||||||
 | 
					    except:
 | 
				
			||||||
 | 
					        return False
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					async def check_subscribe(message_from_user_id, message_chat_id):
 | 
				
			||||||
 | 
					    try:
 | 
				
			||||||
 | 
					        channel_id = CHANNEL_WHITELIST
 | 
				
			||||||
 | 
					        user_channel_status = await bot.get_chat_member(chat_id=channel_id, user_id=message_chat_id)
 | 
				
			||||||
 | 
					        if DEBUG:
 | 
				
			||||||
 | 
					            print('---------------------------------------')
 | 
				
			||||||
 | 
					            print('user_channel_status:',user_channel_status)
 | 
				
			||||||
 | 
					            print('user_channel_status', user_channel_status.status)
 | 
				
			||||||
 | 
					            print('---------------------------------------')
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					        if ((user_channel_status.status != 'left') and (user_channel_status.status != 'kicked')):
 | 
				
			||||||
 | 
					            return True
 | 
				
			||||||
 | 
					        else:
 | 
				
			||||||
 | 
					            await bot.send_message(message_from_user_id, MESSAGES['no_sub'], parse_mode="HTML")
 | 
				
			||||||
 | 
					            return False
 | 
				
			||||||
 | 
					    except:
 | 
				
			||||||
 | 
					        await bot.send_message(message_from_user_id, MESSAGES['error'])
 | 
				
			||||||
 | 
					        return False
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					async def check_access(message):
 | 
				
			||||||
 | 
					    try:
 | 
				
			||||||
 | 
					        if (not checkuser.search_user(message.from_user.id)):
 | 
				
			||||||
 | 
					            # если юзера нет в базе, добавляем
 | 
				
			||||||
 | 
					            try:
 | 
				
			||||||
 | 
					                checkuser.add_user(message.from_user.id)
 | 
				
			||||||
 | 
					            except:
 | 
				
			||||||
 | 
					                if DEBUG:
 | 
				
			||||||
 | 
					                    print("Critical error check_access 1")
 | 
				
			||||||
 | 
					                return False
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					        # checkSubscribe = await check_subscribe(message.from_user.id, message.chat.id)
 | 
				
			||||||
 | 
					        # if (checkSubscribe != True):
 | 
				
			||||||
 | 
					        #     return False
 | 
				
			||||||
 | 
					        print("message_from_user", message.from_user.id)
 | 
				
			||||||
 | 
					        return True
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    except:
 | 
				
			||||||
 | 
					        if DEBUG:
 | 
				
			||||||
 | 
					            print("Critical error check_access 2")
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					async def check_subscribe_spam(message_chat_id):
 | 
				
			||||||
 | 
					    try:
 | 
				
			||||||
 | 
					        channel_id = CHANNEL_WHITELIST
 | 
				
			||||||
 | 
					        user_channel_status = await bot.get_chat_member(chat_id=channel_id, user_id=message_chat_id)
 | 
				
			||||||
 | 
					        if DEBUG:
 | 
				
			||||||
 | 
					            print('---------------------------------------')
 | 
				
			||||||
 | 
					            print('user_channel_status:',user_channel_status)
 | 
				
			||||||
 | 
					            print('user_channel_status', user_channel_status.status)
 | 
				
			||||||
 | 
					            print('---------------------------------------')
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					        if ((user_channel_status.status != 'left') and (user_channel_status.status != 'kicked')):
 | 
				
			||||||
 | 
					            return True
 | 
				
			||||||
 | 
					        else:
 | 
				
			||||||
 | 
					            return False
 | 
				
			||||||
 | 
					    except:
 | 
				
			||||||
 | 
					        return False
 | 
				
			||||||
 | 
					#----------------------------------------
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					# form
 | 
				
			||||||
 | 
					#----------------------------------------
 | 
				
			||||||
 | 
					class Form(StatesGroup):
 | 
				
			||||||
 | 
					    search_0 = State()
 | 
				
			||||||
 | 
					    waiting_for_file = State()
 | 
				
			||||||
 | 
					    waiting_for_file_pause = State()
 | 
				
			||||||
 | 
					    register = State()
 | 
				
			||||||
 | 
					    register_pause = State()
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					    prespam = State()
 | 
				
			||||||
 | 
					    spam = State()
 | 
				
			||||||
 | 
					    spam_pause = State()
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					@dp.message(Command("cancel"))
 | 
				
			||||||
 | 
					@dp.message(F.text.casefold() == "Отмена" or F.text.casefold() == "старт" or F.text.casefold() == "/старт" or F.text.casefold() == "🏠 Главная")
 | 
				
			||||||
 | 
					@dp.message(lambda message: ((message.text == "Отмена") or (message.text == "старт")  or (message.text == "/старт")))
 | 
				
			||||||
 | 
					async def cancel_handler(message: Message, state: FSMContext) -> None:
 | 
				
			||||||
 | 
					    current_state = await state.get_state()
 | 
				
			||||||
 | 
					    checkAccess = await check_access(message)
 | 
				
			||||||
 | 
					    if current_state is None:
 | 
				
			||||||
 | 
					        checkAccess = await check_access(message)
 | 
				
			||||||
 | 
					        if checkAccess:
 | 
				
			||||||
 | 
					            await message.answer(MESSAGES['start'], reply_markup=kb.main_menu)
 | 
				
			||||||
 | 
					        return
 | 
				
			||||||
 | 
					    await state.clear()
 | 
				
			||||||
 | 
					    if checkAccess:
 | 
				
			||||||
 | 
					        await message.answer(MESSAGES['byebye'], reply_markup=kb.main_menu)
 | 
				
			||||||
 | 
					    return
 | 
				
			||||||
 | 
					#----------------------------------------
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					@dp.message(Command("start"))
 | 
				
			||||||
 | 
					async def process_start_command(message: types.Message):
 | 
				
			||||||
 | 
					    checkAccess = await check_access(message)
 | 
				
			||||||
 | 
					    if checkAccess:
 | 
				
			||||||
 | 
					        await message.answer(MESSAGES['start'], reply_markup=kb.main_menu)
 | 
				
			||||||
 | 
					    return
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					@dp.message(StateFilter(None), F.text)
 | 
				
			||||||
 | 
					async def do_main_menu(message: Message, state: FSMContext):
 | 
				
			||||||
 | 
					    txt = message.text
 | 
				
			||||||
 | 
					    try:
 | 
				
			||||||
 | 
					        checkAccess = await check_access(message)
 | 
				
			||||||
 | 
					        if not checkAccess:
 | 
				
			||||||
 | 
					            return await message.answer(MESSAGES['usestart'])
 | 
				
			||||||
 | 
					        if txt == '/admin':
 | 
				
			||||||
 | 
					            checkAdmin = await check_admin(message.chat.id)
 | 
				
			||||||
 | 
					            if checkAdmin:
 | 
				
			||||||
 | 
					                how_users = checkuser.log_info()
 | 
				
			||||||
 | 
					                answer = (f"Пользователей зарегистрировано: {how_users[0]}\n\n"\
 | 
				
			||||||
 | 
					                    f"Рассылка - /spam")
 | 
				
			||||||
 | 
					                return await message.reply(answer)
 | 
				
			||||||
 | 
					            else:
 | 
				
			||||||
 | 
					                return await message.answer(MESSAGES['usestart'])
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					        # elif txt == '/spam':
 | 
				
			||||||
 | 
					        #     checkAdmin = await check_admin(message.chat.id)
 | 
				
			||||||
 | 
					        #     if checkAdmin:
 | 
				
			||||||
 | 
					        #         answer = (f"Для кого рассылка?")
 | 
				
			||||||
 | 
					        #         await message.reply(answer, reply_markup=kb.spam)
 | 
				
			||||||
 | 
					        #         return await state.set_state(Form.prespam)
 | 
				
			||||||
 | 
					        #     else:
 | 
				
			||||||
 | 
					        #         return await message.answer(MESSAGES['usestart'])
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					        # главное меню
 | 
				
			||||||
 | 
					        if txt == '🏠 Главная':
 | 
				
			||||||
 | 
					            return await message.answer(MESSAGES['start'], reply_markup=kb.main_menu)
 | 
				
			||||||
 | 
					        elif txt == '📚 Студентам':
 | 
				
			||||||
 | 
					            return await message.answer(MESSAGES['menu_1'], reply_markup=kb.menu_1)
 | 
				
			||||||
 | 
					        elif txt == '🤝 Работодателям':
 | 
				
			||||||
 | 
					            return await message.answer(MESSAGES['menu_2'], reply_markup=kb.menu_2_inline)
 | 
				
			||||||
 | 
					        elif txt == 'ℹ️ О центре':
 | 
				
			||||||
 | 
					            return await message.answer(MESSAGES['menu_3'], reply_markup=kb.menu_3_inline)
 | 
				
			||||||
 | 
					        # elif txt == '📰 Подписка на новости':
 | 
				
			||||||
 | 
					        #     return await message.answer(MESSAGES['menu_4'], reply_markup=kb.menu_4_inline)
 | 
				
			||||||
 | 
					        # студентам (1)
 | 
				
			||||||
 | 
					        elif txt == '🔙 Назад':
 | 
				
			||||||
 | 
					            return await message.answer(MESSAGES['menu_1'], reply_markup=kb.menu_1)
 | 
				
			||||||
 | 
					        elif txt == '📖 Стажировки, практики и вакансии':
 | 
				
			||||||
 | 
					            return await message.answer(MESSAGES['menu_1_1'], reply_markup=kb.menu_1_1)
 | 
				
			||||||
 | 
					        elif txt == '✍️ Советы по резюме':
 | 
				
			||||||
 | 
					            return await message.answer(MESSAGES['menu_1_2'], reply_markup=kb.menu_1_2_inline)
 | 
				
			||||||
 | 
					        elif txt == '📄 Оформление договора':
 | 
				
			||||||
 | 
					            return await message.answer(MESSAGES['menu_1_3'], reply_markup=kb.menu_1_3_inline)
 | 
				
			||||||
 | 
					        # студентам (1_1)
 | 
				
			||||||
 | 
					        elif txt == '📚 Стажировки':
 | 
				
			||||||
 | 
					            return await message.answer(MESSAGES['menu_1_1_1'], reply_markup=kb.menu_1_1_1_inline)
 | 
				
			||||||
 | 
					        elif txt == '🛠 Практики':
 | 
				
			||||||
 | 
					            return await message.answer(MESSAGES['menu_1_1_2'], reply_markup=kb.menu_1_1_2_inline)
 | 
				
			||||||
 | 
					        elif txt == '💼 Вакансии':
 | 
				
			||||||
 | 
					            return await message.answer(MESSAGES['menu_1_1_3'], reply_markup=kb.menu_1_1_3_inline)
 | 
				
			||||||
 | 
					        else:
 | 
				
			||||||
 | 
					            return await message.answer(MESSAGES['usestart'])
 | 
				
			||||||
 | 
					    # Для выведения ошибок
 | 
				
			||||||
 | 
					    except Exception as e:
 | 
				
			||||||
 | 
					        await message.answer(MESSAGES['error'])
 | 
				
			||||||
 | 
					        print('----------------------------------------')
 | 
				
			||||||
 | 
					        print(f'Critical error in: {e}')
 | 
				
			||||||
 | 
					        print('----------------------------------------')
 | 
				
			||||||
 | 
					#----------------------------------------
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					if __name__ == '__main__':
 | 
				
			||||||
 | 
					    asyncio.run(main())
 | 
				
			||||||
		Loading…
	
	
			
			x
			
			
		
	
		Reference in New Issue
	
	Block a user