\n\n\n\n Ho creato un bot di Telegram che pianifica i miei messaggi - AI7Bot \n

Ho creato un bot di Telegram che pianifica i miei messaggi

📖 12 min read2,268 wordsUpdated Apr 3, 2026

Hey a tutti, Marcus qui da ai7bot.com. Oggi voglio parlare di qualcosa che ha suscitato molto interesse nei miei progetti di sviluppo personali ultimamente: i bot di Telegram. In particolare, voglio esplorare come rendere il tuo bot di Telegram non solo un risponditore, ma un pianificatore. Dimentica le semplici cose tipo “hello world”; costruiremo un bot che ricorda le cose per te e invia messaggi a orari specifici. Pensalo come il tuo assistente digitale personale e silenzioso, che vive proprio all’interno delle tue chat di Telegram.

Ricordo che alcuni mesi fa stavo cercando di coordinare una sessione settimanale di D&D con il mio gruppo. Continuavamo a dimenticare chi ospitava, a che ora ci eravamo messi d’accordo e quali snack ognuno portava. Abbiamo provato a usare note condivise, calendari, di tutto. Ma il denominatore comune era sempre Telegram. È stato allora che mi è venuta l’idea: perché non creare un bot che ci ricordi? Non solo un promemoria occasionale, ma qualcosa di ricorrente, qualcosa che si adatti. Quella piccola frustrazione mi ha portato in un labirinto, e ciò che ho trovato si è rivelato sorprendentemente semplice da implementare una volta superata la configurazione iniziale.

Oltre le Risposte Semplici: Il Potere dei Messaggi Programmati

La maggior parte dei bot di Telegram di base sono reattivi. Invia un comando, e loro rispondono. Va bene per query semplici, ma non sfrutta davvero il pieno potenziale di un bot. La vera magia avviene quando il tuo bot può essere proattivo: quando può iniziare conversazioni, inviare aggiornamenti o ricordarti qualcosa senza che tu debba sollecitarlo per primo. È qui che entrano in gioco i messaggi programmati.

Immagina un bot che:

  • Ricorda al tuo team degli stand-up quotidiani cinque minuti prima che inizino.
  • Ti invia una previsione del tempo personalizzata ogni mattina alle 7 AM.
  • Ti notifica riguardo le scadenze importanti per un progetto.
  • Pinge il tuo gruppo di D&D ogni domenica alle 3 PM con un messaggio “sessione in arrivo!”

Le possibilità sono infinite. E la parte migliore? Non è così complicato come potresti pensare. Useremo Python, un linguaggio popolare per lo sviluppo di bot, e un paio di librerie affidabili.

Di Cosa Avremo Bisogno: Gli Strumenti Fondamentali

Prima di tuffarci nel codice, elenchiamo i nostri strumenti:

  1. Python 3: Se non lo hai, procuratelo. È la spina dorsale del nostro bot.
  2. python-telegram-bot library: Questa è la nostra interfaccia principale con il Telegram Bot API. Gestisce tutta la comunicazione complicata.
  3. APScheduler library: Questa è la star dello spettacolo per la programmazione. Ci permette di eseguire funzioni a orari o intervalli specifici.

Puoi installare le librerie Python utilizzando pip:


pip install python-telegram-bot APScheduler

E, ovviamente, avrai bisogno di un token per il bot di Telegram. Se non hai ancora creato un bot, vai su BotFather su Telegram, invialo /newbot e segui le istruzioni. Ti darà un token – conservalo al sicuro!

Impostare la Struttura di Base del Bot

Iniziamo a far funzionare il nostro bot di Telegram di base. Questa parte dovrebbe essere familiare se hai già fatto sviluppo di bot in precedenza.


from telegram import Update
from telegram.ext import Application, CommandHandler, ContextTypes

# Sostituisci con il tuo token reale del bot fornito da BotFather
BOT_TOKEN = "YOUR_TELEGRAM_BOT_TOKEN"

async def start(update: Update, context: ContextTypes.DEFAULT_TYPE) -> None:
 """Invia un messaggio di saluto quando viene emesso il comando /start."""
 await update.message.reply_text("Ciao! Sono il tuo bot per la pianificazione. Usa /help per vedere cosa posso fare.")

async def help_command(update: Update, context: ContextTypes.DEFAULT_TYPE) -> None:
 """Invia un messaggio di aiuto."""
 await update.message.reply_text("Posso programmare messaggi per te. Prova /schedule per impostare un promemoria!")

def main() -> None:
 """Avvia il bot."""
 application = Application.builder().token(BOT_TOKEN).build()

 application.add_handler(CommandHandler("start", start))
 application.add_handler(CommandHandler("help", help_command))

 print("Bot avviato e in ascolto...")
 application.run_polling(allowed_updates=Update.ALL_TYPES)

if __name__ == "__main__":
 main()

Esegui questo script, e se invii /start o /help al tuo bot, dovresti ricevere una risposta. Questa è la nostra base. Ora, portiamo in gioco il pianificatore.

Introducendo APScheduler: Il Tuo Cronometrista

APScheduler sta per “Advanced Python Scheduler.” È una libreria solida che ti permette di programmare funzioni Python per essere eseguite a orari, date o intervalli specifici. Useremo il suo BlockingScheduler, che opera nel thread principale della nostra applicazione.

Il concetto fondamentale è questo: quando un utente dice al nostro bot di programmare qualcosa, memorizzeremo quella richiesta e utilizzeremo APScheduler per aggiungere un lavoro. Quando arriverà il momento, APScheduler eseguirà una funzione che invia il messaggio all’utente.

Programmando il Nostro Primo Messaggio

Dobbiamo modificare il nostro bot per includere capacità di programmazione. Inizieremo con un comando semplice, /schedule, che prenderà un messaggio e un orario (ad esempio, “tra 5 minuti”).


from telegram import Update
from telegram.ext import Application, CommandHandler, ContextTypes
from apscheduler.schedulers.blocking import BlockingScheduler
from datetime import datetime, timedelta
import asyncio

# Sostituisci con il tuo effettivo token del bot
BOT_TOKEN = "YOUR_TELEGRAM_BOT_TOKEN"

# Inizializza il pianificatore
scheduler = BlockingScheduler()

async def start(update: Update, context: ContextTypes.DEFAULT_TYPE) -> None:
 """Invia un messaggio di saluto."""
 await update.message.reply_text("Ciao! Sono il tuo bot per la pianificazione. Usa /help per vedere cosa posso fare.")

async def help_command(update: Update, context: ContextTypes.DEFAULT_TYPE) -> None:
 """Invia un messaggio di aiuto."""
 await update.message.reply_text(
 "Posso programmare messaggi per te. Prova /schedule <minuti> <tuo messaggio>.\n"
 "Esempio: /schedule 5 Ricorda di comprare la spesa!"
 )

async def send_scheduled_message(chat_id: int, message_text: str, application: Application) -> None:
 """Invia il messaggio programmato effettivo."""
 # Dobbiamo ottenere l'istanza del bot per inviare messaggi al di fuori di un contesto di aggiornamento
 await application.bot.send_message(chat_id=chat_id, text=message_text)
 print(f"Inviato messaggio programmato a {chat_id}: {message_text}")

async def schedule_command(update: Update, context: ContextTypes.DEFAULT_TYPE) -> None:
 """Programma un messaggio."""
 if not context.args or len(context.args) < 2:
 await update.message.reply_text(
 "Uso: /schedule <minuti> <tuo messaggio>.\n"
 "Esempio: /schedule 5 Ricorda di comprare la spesa!"
 )
 return

 try:
 minutes = int(context.args[0])
 if minutes <= 0:
 await update.message.reply_text("I minuti devono essere un numero positivo.")
 return
 
 message_to_schedule = " ".join(context.args[1:])
 
 # Calcola il tempo futuro
 run_time = datetime.now() + timedelta(minutes=minutes)
 
 # Aggiungi il lavoro al pianificatore
 # Dobbiamo passare l'istanza dell'applicazione affinché send_scheduled_message possa accedervi
 scheduler.add_job(
 send_scheduled_message, 
 'date', 
 run_date=run_time, 
 args=[update.effective_chat.id, message_to_schedule, context.application]
 )
 
 await update.message.reply_text(
 f"Ok, ti ricorderò tra {minutes} minuto(i) alle {run_time.strftime('%H:%M:%S')}!"
 )
 print(f"Lavoro programmato per {update.effective_chat.id} alle {run_time} con messaggio: {message_to_schedule}")

 except ValueError:
 await update.message.reply_text("Per favore fornisci un numero valido per i minuti.")
 except Exception as e:
 await update.message.reply_text(f"Qualcosa è andato storto: {e}")

def main() -> None:
 """Avvia il bot e il pianificatore."""
 application = Application.builder().token(BOT_TOKEN).build()

 application.add_handler(CommandHandler("start", start))
 application.add_handler(CommandHandler("help", help_command))
 application.add_handler(CommandHandler("schedule", schedule_command))

 # Avvia il pianificatore in un thread o processo separato se hai bisogno di un comportamento non bloccante
 # Per semplicità, lo eseguiremo nel thread principale con run_polling.
 # Il BlockingScheduler di APScheduler blocca, quindi dobbiamo eseguirlo in modo concorrente.
 # Un pattern comune è eseguire il pianificatore in un thread separato.
 
 # Iniziamo il pianificatore in modo non bloccante per l'uso in produzione
 # usando BackgroundScheduler o mettendo BlockingScheduler in un thread separato.
 # Per questo esempio, modificheremo leggermente come opera main.
 
 # Il BlockingScheduler di APScheduler bloccherà il thread principale.
 # Per farlo funzionare con application.run_polling() di python-telegram-bot,
 # dobbiamo assicurarci che il pianificatore venga eseguito senza bloccare gli aggiornamenti del bot.
 # Un modo semplice per farlo è utilizzare un BackgroundScheduler.

 from apscheduler.schedulers.background import BackgroundScheduler
 global scheduler # Re-inizializza il pianificatore per BackgroundScheduler
 scheduler = BackgroundScheduler()
 scheduler.start()

 print("Bot avviato e in ascolto...")
 application.run_polling(allowed_updates=Update.ALL_TYPES)
 
 # Spegni il pianificatore quando il bot si ferma
 scheduler.shutdown()

if __name__ == "__main__":
 main()

Una nota veloce su BlockingScheduler vs. BackgroundScheduler: Nei miei test iniziali per questo articolo, ho rapidamente realizzato che BlockingScheduler (come suggerisce il nome) blocca il thread principale. Ciò significa che il tuo bot non sarà in grado di ricevere nuovi aggiornamenti da Telegram mentre il pianificatore è attivo. Non ideale! La soluzione è utilizzare BackgroundScheduler, che viene eseguito in un thread separato, permettendo al tuo bot di rimanere reattivo. Ho aggiornato la funzione main() nel frammento sopra per riflettere questo.

Ora, se esegui questo script aggiornato, puoi inviare al tuo bot qualcosa come /schedule 1 Test reminder! e dopo un minuto, il tuo bot dovrebbe inviarti “Test reminder!”. Che figata, vero?

Rendere tutto più flessibile: Lavori ricorrenti

I promemoria una tantum vanno bene, ma che ne è degli eventi ricorrenti? APScheduler rende tutto incredibilmente semplice con i suoi trigger interval e cron. Aggiungiamo un comando per pianificare un messaggio ogni X minuti.


# ... (importazioni e inizializzazioni precedenti) ...

async def schedule_recurring_command(update: Update, context: ContextTypes.DEFAULT_TYPE) -> None:
 """Pianifica un messaggio ricorrente."""
 if not context.args or len(context.args) < 2:
 await update.message.reply_text(
 "Utilizzo: /schedule_every <minutes> <il tuo messaggio>.\n"
 "Esempio: /schedule_every 60 Controllo orario!"
 )
 return

 try:
 minutes_interval = int(context.args[0])
 if minutes_interval <= 0:
 await update.message.reply_text("I minuti devono essere un numero positivo.")
 return
 
 message_to_schedule = " ".join(context.args[1:])
 chat_id = update.effective_chat.id
 
 # Aggiungi il lavoro ricorrente al pianificatore
 job_id = f"recurring_job_{chat_id}_{datetime.now().timestamp()}" # ID unico per una potenziale rimozione
 scheduler.add_job(
 send_scheduled_message, 
 'interval', 
 minutes=minutes_interval, 
 args=[chat_id, message_to_schedule, context.application],
 id=job_id,
 replace_existing=True # Facoltativo: sostituisci se l'ID esiste
 )
 
 await update.message.reply_text(
 f"Va bene, ti ricorderò ogni {minutes_interval} minuto(i) con: '{message_to_schedule}'"
 )
 print(f"Lavoro ricorrente '{job_id}' programmato per {chat_id} ogni {minutes_interval} minuti.")

 except ValueError:
 await update.message.reply_text("Per favore, fornisci un numero valido per i minuti.")
 except Exception as e:
 await update.message.reply_text(f"C'è stato un problema: {e}")

# ... (aggiungi questo gestore nella funzione main() ...) 
# application.add_handler(CommandHandler("schedule_every", schedule_recurring_command))

Ricorda di aggiungere il nuovo gestore di comandi nella tua funzione main():


def main() -> None:
 # ... gestori esistenti ...
 application.add_handler(CommandHandler("schedule_every", schedule_recurring_command))
 # ... resto della main() ...

Ora puoi dire al tuo bot /schedule_every 15 Non dimenticare di fare stretching! e ti ricorderà duttilmente ogni 15 minuti. Qui è dove il promemoria per la sessione di D&D ha davvero fatto clic per me. Potevo impostarlo una volta e sarebbe funzionato ogni settimana.

Gestire lo stato e la persistenza (Un passaggio necessario)

In questo momento, se riavvii il tuo bot, tutti i lavori programmati andranno persi. Non è l’ideale per un pianificatore affidabile. Per un bot nel mondo reale, vorresti memorizzare questi lavori programmati in un database (come SQLite, PostgreSQL, o anche un semplice file JSON) e ricaricarli quando il bot si avvia. APScheduler ha supporto integrato per i job store, il che rende tutto relativamente semplice.

Per un bot in produzione, ti consiglio vivamente di aggiungere un job store. Ecco un contorno concettuale di come integrarlo con SQLite:


from apscheduler.jobstores.sqlalchemy import SQLAlchemyJobStore

# ... (resto delle importazioni e del codice) ...

# Nella tua funzione main():
def main() -> None:
 # ... configurazione esistente dell'applicazione ...

 jobstores = {
 'default': SQLAlchemyJobStore(url='sqlite:///jobs.sqlite')
 }
 
 # Re-inizializza il pianificatore con job store
 global scheduler
 scheduler = BackgroundScheduler(jobstores=jobstores)
 scheduler.start()

 # ... resto della main() ...

Quando utilizzi un job store, APScheduler gestisce la serializzazione e deserializzazione dei lavori. Questo significa che anche se il tuo bot crasha o si riavvia, riprenderà tutti i suoi vecchi lavori esattamente da dove si era fermato. Questo è cruciale per qualsiasi applicazione seria.

Takeaway pratici per il tuo bot

Costruire un bot che può pianificare messaggi apre un nuovo mondo di possibilità. Ecco cosa ho imparato e cosa dovresti considerare:

  1. Inizia semplice: Non cercare di costruire subito il pianificatore più complesso. Fai funzionare prima un promemoria una tantum, poi aggiungi lavori ricorrenti.
  2. La gestione degli errori è fondamentale: Gli utenti inevitabilmente inseriscono comandi sbagliati o orari non validi. Il tuo bot deve essere abbastanza solido da gestire questi errori senza problemi. Aggiungi blocchi try-except!
  3. La persistenza è non negoziabile: Per qualsiasi bot che ti aspetti funzioni per più di qualche minuto, devi assolutamente memorizzare i lavori programmati. I job store di APScheduler rendono tutto semplice. SQLite è un ottimo punto di partenza per l’archiviazione locale.
  4. Feedback dell’utente: Conferma sempre con l’utente che il loro programma è stato impostato. “Va bene, ti ricorderò tra 5 minuti!” fa una grande differenza.
  5. Istruzioni chiare: Fornisci buoni messaggi /help con esempi. Aiuta gli utenti a capire come interagire con il tuo bot.
  6. Considera i fusi orari: Per un bot globale, i fusi orari possono essere un incubo. APScheduler può gestirli, ma aggiunge complessità. Per un bot personale, potresti cavartela usando semplicemente l’UTC o l’ora locale del server.

Questo viaggio da un semplice promemoria di D&D a un bot pianificatore più capace è stato incredibilmente gratificante. Dimostra che con alcune buone librerie e un po’ di Python, puoi elevare i tuoi bot Telegram da semplici risponditori a veri assistenti proattivi. Provalo, sperimenta e fammi sapere quali idee interessanti di pianificazione ti vengono in mente!

Buona costruzione di bot!

🕒 Published:

💬
Written by Jake Chen

Bot developer who has built 50+ chatbots across Discord, Telegram, Slack, and WhatsApp. Specializes in conversational AI and NLP.

Learn more →
Browse Topics: Best Practices | Bot Building | Bot Development | Business | Operations
Scroll to Top