feat: enhance message handling with content pattern matching and update environment configuration
This commit is contained in:
+52
-3
@@ -1,5 +1,6 @@
|
||||
import logging
|
||||
import os
|
||||
import re
|
||||
import time
|
||||
from datetime import datetime, timedelta
|
||||
|
||||
@@ -42,15 +43,55 @@ def should_delete_message(
|
||||
webhook_id: str,
|
||||
author_id: str,
|
||||
cutoff: int,
|
||||
content_pattern: str | None = None,
|
||||
) -> bool:
|
||||
message_timestamp = int(parse_message_timestamp(message).timestamp())
|
||||
return (
|
||||
message_timestamp <= cutoff
|
||||
and message.get("webhook_id") == webhook_id
|
||||
and message.get("author", {}).get("id") == author_id
|
||||
and message_matches_pattern(message, content_pattern)
|
||||
)
|
||||
|
||||
|
||||
def message_matches_pattern(message: dict, content_pattern: str | None = None) -> bool:
|
||||
"""Return True when message content/embed text matches the optional pattern."""
|
||||
if not content_pattern:
|
||||
return True
|
||||
|
||||
text_chunks: list[str] = []
|
||||
content = message.get("content")
|
||||
if isinstance(content, str) and content:
|
||||
text_chunks.append(content)
|
||||
|
||||
embeds = message.get("embeds")
|
||||
if isinstance(embeds, list):
|
||||
for embed in embeds:
|
||||
if not isinstance(embed, dict):
|
||||
continue
|
||||
title = embed.get("title")
|
||||
description = embed.get("description")
|
||||
if isinstance(title, str) and title:
|
||||
text_chunks.append(title)
|
||||
if isinstance(description, str) and description:
|
||||
text_chunks.append(description)
|
||||
|
||||
footer = embed.get("footer")
|
||||
if isinstance(footer, dict):
|
||||
footer_text = footer.get("text")
|
||||
if isinstance(footer_text, str) and footer_text:
|
||||
text_chunks.append(footer_text)
|
||||
|
||||
if not text_chunks:
|
||||
return False
|
||||
|
||||
searchable_text = "\n".join(text_chunks)
|
||||
try:
|
||||
return re.search(content_pattern, searchable_text, flags=re.IGNORECASE) is not None
|
||||
except re.error:
|
||||
return content_pattern.lower() in searchable_text.lower()
|
||||
|
||||
|
||||
def get_rate_limit_retry_after(response: requests.Response) -> float | None:
|
||||
header_retry_after = parse_float(response.headers.get("Retry-After"))
|
||||
if header_retry_after is not None:
|
||||
@@ -137,7 +178,7 @@ def find_last_message_by_author(
|
||||
return None
|
||||
|
||||
|
||||
def fetch_messages_to_delete(headers: dict, channel_id: str, webhook_id: str, author_id: str, cutoff: int, last_message_id: str | None = None) -> tuple[list[dict], str | None]:
|
||||
def fetch_messages_to_delete(headers: dict, channel_id: str, webhook_id: str, author_id: str, cutoff: int, last_message_id: str | None = None, content_pattern: str | None = None) -> tuple[list[dict], str | None]:
|
||||
"""
|
||||
Fetch messages from the channel that are older than the cutoff timestamp and sent by the webhook.
|
||||
Uses pagination with the 'before' parameter to resume from the last processed message.
|
||||
@@ -180,6 +221,7 @@ def fetch_messages_to_delete(headers: dict, channel_id: str, webhook_id: str, au
|
||||
webhook_id,
|
||||
author_id,
|
||||
cutoff,
|
||||
content_pattern,
|
||||
):
|
||||
delete_list.append(build_delete_entry(message))
|
||||
|
||||
@@ -240,7 +282,7 @@ def delete_message(headers: dict, channel_id: str, message_id: str) -> tuple[boo
|
||||
return False, None, False
|
||||
|
||||
|
||||
def delete_old_messages(minutes: int = 6) -> None:
|
||||
def delete_old_messages(minutes: int = 6, content_pattern: str | None = None) -> None:
|
||||
"""
|
||||
Delete all messages sent by the webhook in the last `minutes` minutes.
|
||||
Uses a dynamic slowdown to avoid hitting Discord API rate limits and pagination to fetch all messages.
|
||||
@@ -283,6 +325,7 @@ def delete_old_messages(minutes: int = 6) -> None:
|
||||
webhook_id,
|
||||
author_id,
|
||||
cutoff,
|
||||
content_pattern,
|
||||
):
|
||||
anchor_message = build_delete_entry(last_author_message)
|
||||
deleted, wait_seconds, abort_batch = delete_message(
|
||||
@@ -303,7 +346,13 @@ def delete_old_messages(minutes: int = 6) -> None:
|
||||
|
||||
while True:
|
||||
delete_list, next_last_message_id = fetch_messages_to_delete(
|
||||
headers, discord_channel_id, webhook_id, author_id, cutoff, last_message_id
|
||||
headers,
|
||||
discord_channel_id,
|
||||
webhook_id,
|
||||
author_id,
|
||||
cutoff,
|
||||
last_message_id,
|
||||
content_pattern,
|
||||
)
|
||||
|
||||
if not delete_list:
|
||||
|
||||
Reference in New Issue
Block a user