Prevent Discord bot from posting when channel is inactive after its last message

I have a Python Discord bot that automatically posts random content every 6 hours using a background task. The issue I’m facing is that the bot keeps posting even when nobody has written anything in the channel since its last message.

I want to modify the bot so it checks if there have been any new messages from real users after its previous post. If the channel is silent (no user activity), the bot should skip sending the next scheduled message.

Here’s my current setup:

import os
import discord
import asyncio
import random
from content import quotes_array
from copy import deepcopy

token = os.environ['DISCORD_TOKEN']

bot = discord.Client()

async def scheduled_posting():
    await bot.wait_until_ready()
    quotes = deepcopy(quotes_array)
    original_quotes = deepcopy(quotes_array)
    while not bot.is_closed:
        target_channel = bot.get_channel("CHANNEL_ID")
        if not quotes:
            quotes = deepcopy(original_quotes)
        await bot.send_message(target_channel, quotes.pop(random.randrange(0, len(quotes))))
        await asyncio.sleep(21600)

bot.loop.create_task(scheduled_posting())
bot.run(token)

What’s the best approach to track channel activity and prevent unnecessary bot posts?

You need to check the channel’s recent messages before posting to see if users are active. I had the same problem with my announcement bot - fixed it by saving when the bot last posted, then using channel.history() to see if any real users posted after that.

Drop this before your posting code:

last_bot_message_time = None
async for message in target_channel.history(limit=10):
    if message.author == bot.user:
        last_bot_message_time = message.created_at
        break
        
if last_bot_message_time:
    user_messages = [msg async for msg in target_channel.history(after=last_bot_message_time) if not msg.author.bot]
    if not user_messages:
        continue  # Skip posting

This worked great for months with zero database setup. Just handle the edge case where your bot hasn’t posted yet - check if last_bot_message_time is None.

Automate this instead of manually checking message history. I’ve dealt with this exact problem running multiple community bots - Python becomes a nightmare when you scale.

The real issue isn’t just checking activity. You need to handle edge cases: bot restarts, rate limits, channels getting deleted and recreated.

I moved my Discord posting logic to Latenode. It handles everything cleanly:

  • Pulls recent messages from Discord API
  • Filters by timestamp and author type
  • Stores last successful post time in workflow memory
  • Only triggers posting when real users are active
  • Built-in retry logic if Discord API goes down

The workflow runs on schedule without keeping a Python process alive. You can add conditions like posting different content based on channel activity, or skip posting during certain hours.

You can also duplicate the workflow for other servers without managing separate bot instances. Way cleaner than tracking state in Python scripts.

Check it out: https://latenode.com

Use the on_message event to track posts and set a flag. Way easier than constantly fetching message history. I do this with my meme bot - when someone messages, I flip user_activity = True then reset it to False after posting. Just check that boolean in your scheduled task.

Skip Discord’s message history and track timestamps yourself in a simple database or file. I learned this the hard way - after months of runtime, searching through thousands of messages got painfully slow and unreliable. Set up a lightweight SQLite database to store when your bot posted and when users last messaged. Update user timestamps with on_message events, then compare during your scheduled task. This survived multiple bot restarts and Discord outages without losing track. The database overhead is tiny but gives you persistence that in-memory solutions can’t. Plus you can expand it later to track activity patterns per channel when you hit multiple servers. Way more reliable than constantly hammering Discord’s API.

Track channel activity by storing when your bot last posted and checking if users have been active since then. I had this exact problem with a quotes bot that wouldn’t stop spamming dead channels. Save your message timestamp after each post, then before the next scheduled post, use channel.history(after=last_post_timestamp, limit=50) to check for non-bot messages. If nothing comes back, skip posting. python last_post_time = None if last_post_time: recent_messages = [msg async for msg in target_channel.history(after=last_post_time) if not msg.author.bot] if len(recent_messages) == 0: await asyncio.sleep(21600) continue This has worked solid for me across three servers for six months. The big advantage over just checking the last message is it handles cases where other bots post between your message and actual user activity. Store the timestamp in a global variable or simple text file so it survives restarts.

Your code needs to track the last message timestamp and compare it with your bot’s last post. But managing this manually in Python gets messy fast.

I had a similar setup with multiple Discord bots across different servers with complex posting rules. Writing all that state management and timing logic by hand was a nightmare to maintain.

Moving everything to Latenode worked way better. You can build a workflow that:

  • Grabs the last few messages from your Discord channel via API
  • Filters out bot messages to check for real user activity
  • Compares timestamps to see if users posted after your last bot message
  • Only posts quotes if there was actual user engagement
  • Handles scheduling automatically

You don’t need your Python script running 24/7 or worry about connection drops. Latenode handles reliability while you focus on the logic.

You can add more rules later - different content based on activity levels or time of day - without rewriting your entire bot.

Check it out: https://latenode.com

Store your bot’s user ID and check if the last message in the channel is from your bot. If it is, skip the scheduled post.

async def should_post_message(channel):
    last_message = await channel.fetch_message(channel.last_message_id)
    return last_message.author.id != bot.user.id

Just add this check before your posting logic in the scheduled task. I did something similar for a gaming server where my bot was spamming quotes during quiet periods. Way simpler than looping through message history and performs better since you’re only fetching one message.

Biggest advantage? You won’t hit API rate limits from constantly checking channel history. Just handle cases where last_message_id might be None if the channel’s completely empty.