Spaces:
Sleeping
Sleeping
| import logging | |
| import asyncio | |
| from dotenv import load_dotenv | |
| import os | |
| from telegram import Update, ForceReply | |
| from telegram.ext import ( | |
| Application, CommandHandler, MessageHandler, ContextTypes, filters, ConversationHandler | |
| ) | |
| from tools import add_task, list_tasks, edit_task, delete_task | |
| from runner import create_session_async, run_agent | |
| from db_utils import save_message, load_chat_history, init_db | |
| logging.basicConfig( | |
| format="%(asctime)s - %(name)s - %(levelname)s - %(message)s", level=logging.INFO | |
| ) | |
| logger = logging.getLogger(__name__) | |
| load_dotenv() | |
| session = None | |
| NEW_TASK, EDIT_TASK_NAME, EDIT_TASK_NEW_NAME, DELETE_TASK_NAME, DELETE_TASK_CONFIRM = range(5) | |
| async def start(update: Update, context: ContextTypes.DEFAULT_TYPE) -> None: | |
| menu = ( | |
| "Welcome to Task Manager Bot!\n" | |
| "Choose a method:\n" | |
| "/newtask - Add a new task\n" | |
| "/listtask - View all tasks\n" | |
| "/edittask - Edit an existing task\n" | |
| "/deletetask - Delete a task\n" | |
| "/history - Show last 5 chats" | |
| ) | |
| await update.message.reply_text(menu, reply_markup=ForceReply(selective=True)) | |
| async def newtask_start(update: Update, context: ContextTypes.DEFAULT_TYPE) -> int: | |
| await update.message.reply_text("Enter task name:") | |
| return NEW_TASK | |
| async def newtask_save(update: Update, context: ContextTypes.DEFAULT_TYPE) -> int: | |
| user_id = str(update.effective_user.id) | |
| task_name = update.message.text.strip() | |
| if task_name: | |
| result = add_task(user_id, task_name) | |
| await update.message.reply_text(result) | |
| else: | |
| await update.message.reply_text("Task name cannot be empty. Please try again.") | |
| return NEW_TASK | |
| return ConversationHandler.END | |
| async def listtask(update: Update, context: ContextTypes.DEFAULT_TYPE) -> None: | |
| user_id = str(update.effective_user.id) | |
| result = list_tasks(user_id) | |
| await update.message.reply_text(result) | |
| async def edittask_start(update: Update, context: ContextTypes.DEFAULT_TYPE) -> int: | |
| await update.message.reply_text("Enter the task name you want to edit:") | |
| return EDIT_TASK_NAME | |
| async def edittask_get_new_name(update: Update, context: ContextTypes.DEFAULT_TYPE) -> int: | |
| user_id = str(update.effective_user.id) | |
| old_name = update.message.text.strip() | |
| context.user_data['edit_task_old_name'] = old_name | |
| tasks_list = list_tasks(user_id) | |
| if old_name not in tasks_list: | |
| await update.message.reply_text("Task not found. Please enter a valid task name:") | |
| return EDIT_TASK_NAME | |
| await update.message.reply_text("Enter the new task name:") | |
| return EDIT_TASK_NEW_NAME | |
| async def edittask_save(update: Update, context: ContextTypes.DEFAULT_TYPE) -> int: | |
| user_id = str(update.effective_user.id) | |
| new_name = update.message.text.strip() | |
| old_name = context.user_data.get('edit_task_old_name') | |
| result = edit_task( user_id, old_name, new_name) | |
| await update.message.reply_text(result) | |
| return ConversationHandler.END | |
| async def deletetask_start(update: Update, context: ContextTypes.DEFAULT_TYPE) -> int: | |
| await update.message.reply_text("Enter the task name you want to delete:") | |
| return DELETE_TASK_NAME | |
| async def deletetask_confirm(update: Update, context: ContextTypes.DEFAULT_TYPE) -> int: | |
| user_id = str(update.effective_user.id) | |
| task_name = update.message.text.strip() | |
| context.user_data['delete_task_name'] = task_name | |
| tasks_list = list_tasks(user_id) | |
| if task_name not in tasks_list: | |
| await update.message.reply_text("Task not found. Please enter a valid task name:") | |
| return DELETE_TASK_NAME | |
| await update.message.reply_text(f'Are you sure you want to delete "{task_name}"? If yes, type "yes" else type /cancel') | |
| return DELETE_TASK_CONFIRM | |
| async def deletetask_finish(update: Update, context: ContextTypes.DEFAULT_TYPE) -> int: | |
| user_id = str(update.effective_user.id) | |
| response = update.message.text.strip().lower() | |
| task_name = context.user_data.get('delete_task_name') | |
| if response == "yes": | |
| result = delete_task(user_id, task_name) | |
| await update.message.reply_text(result) | |
| else: | |
| await update.message.reply_text("Delete cancelled ❌") | |
| return ConversationHandler.END | |
| async def cancel(update: Update, context: ContextTypes.DEFAULT_TYPE) -> int: | |
| await update.message.reply_text("Cancelled ❌") | |
| return ConversationHandler.END | |
| async def history(update: Update, context: ContextTypes.DEFAULT_TYPE) -> None: | |
| user_id = str(update.effective_user.id) | |
| messages = load_chat_history(user_id, limit=5) | |
| if not messages: | |
| await update.message.reply_text("No history yet.") | |
| return | |
| history_text = "\n".join([f"[{m.role}] {m.message}" for m in messages]) | |
| await update.message.reply_text("🕑 Your recent chats:\n\n" + history_text) | |
| async def handle_free_text(update: Update, context: ContextTypes.DEFAULT_TYPE) -> None: | |
| user_id = int(update.effective_user.id) | |
| user_message = update.message.text.strip() | |
| save_message(user_id, "user", user_message) | |
| await update.message.reply_text(f"🤖 Thinking... {user_id}") | |
| try: | |
| response = await run_agent(user_id, session.id, user_message) | |
| if not response: | |
| response_text = "⚠️ I didn't get any response." | |
| elif isinstance(response, dict): | |
| response_text = response.get("text") or response.get("message") or str(response) | |
| else: | |
| response_text = str(response).strip() | |
| # if not response_text: | |
| # response_text = "⚠️ Sorry, I got an empty reply." | |
| save_message(user_id, "bot", response_text) | |
| await update.message.reply_text(response_text) | |
| except Exception as e: | |
| await update.message.reply_text(f"❌ Error: {str(e)}") | |
| def main(): | |
| global session | |
| init_db() | |
| loop = asyncio.get_event_loop() | |
| session = loop.run_until_complete(create_session_async()) | |
| telegram_token = os.getenv("TELEGRAM_BOT_TOKEN") | |
| application = Application.builder().token(telegram_token).build() | |
| application.add_handler(CommandHandler("start", start)) | |
| application.add_handler(CommandHandler("listtask", listtask)) | |
| application.add_handler(CommandHandler("history", history)) | |
| newtask_conv = ConversationHandler( | |
| entry_points=[CommandHandler("newtask", newtask_start)], | |
| states={NEW_TASK: [MessageHandler(filters.TEXT & ~filters.COMMAND, newtask_save)]}, | |
| fallbacks=[] | |
| ) | |
| application.add_handler(newtask_conv) | |
| edittask_conv = ConversationHandler( | |
| entry_points=[CommandHandler("edittask", edittask_start)], | |
| states={ | |
| EDIT_TASK_NAME: [MessageHandler(filters.TEXT & ~filters.COMMAND, edittask_get_new_name)], | |
| EDIT_TASK_NEW_NAME: [MessageHandler(filters.TEXT & ~filters.COMMAND, edittask_save)] | |
| }, | |
| fallbacks=[] | |
| ) | |
| application.add_handler(edittask_conv) | |
| deletetask_conv = ConversationHandler( | |
| entry_points=[CommandHandler("deletetask", deletetask_start)], | |
| states={ | |
| DELETE_TASK_NAME: [MessageHandler(filters.TEXT & ~filters.COMMAND, deletetask_confirm)], | |
| DELETE_TASK_CONFIRM: [MessageHandler(filters.TEXT & ~filters.COMMAND, deletetask_finish)] | |
| }, | |
| fallbacks=[CommandHandler("cancel", cancel)] | |
| ) | |
| application.add_handler(deletetask_conv) | |
| application.add_handler(CommandHandler("cancel", cancel)) | |
| application.add_handler( | |
| MessageHandler(filters.TEXT & ~filters.COMMAND, handle_free_text) | |
| ) | |
| application.run_polling() | |
| if __name__ == "__main__": | |
| main() | |