From 39724fb3fa5e4dbc8a99c5a556e6ac42493ed6c1 Mon Sep 17 00:00:00 2001 From: Fuwn Date: Wed, 17 Sep 2025 18:36:00 -0700 Subject: refactor(media_required): Rename to roleplay_media_required --- src/umabot/bot.py | 4 +- src/umabot/rules/__init__.py | 4 +- src/umabot/rules/media_required.py | 113 ---------------------------- src/umabot/rules/roleplay_media_required.py | 113 ++++++++++++++++++++++++++++ 4 files changed, 117 insertions(+), 117 deletions(-) delete mode 100644 src/umabot/rules/media_required.py create mode 100644 src/umabot/rules/roleplay_media_required.py (limited to 'src') diff --git a/src/umabot/bot.py b/src/umabot/bot.py index 667f098..87068a5 100644 --- a/src/umabot/bot.py +++ b/src/umabot/bot.py @@ -9,7 +9,7 @@ from socketserver import ThreadingMixIn from loguru import logger from .config import Config -from .rules import SpamDetector, RoleplayLimiter, MediaRequiredRule, RoleplayWordCountRule +from .rules import SpamDetector, RoleplayLimiter, RoleplayMediaRequiredRule, RoleplayWordCountRule # from .rules import StaticRoleplayLimiter # Disabled by default - uncomment to use static limiting @@ -76,7 +76,7 @@ class UmaBot: # Initialize rules self.rules = [ SpamDetector(config), - MediaRequiredRule(config), # Requires media for roleplay posts + RoleplayMediaRequiredRule(config), # Requires media for roleplay posts RoleplayWordCountRule(config), # Sends short roleplay posts to mod queue RoleplayLimiter(config, self.subreddit) # Surge-based roleplay limiter (default) # StaticRoleplayLimiter(config) # Uncomment to use static roleplay limiting instead diff --git a/src/umabot/rules/__init__.py b/src/umabot/rules/__init__.py index 4296ab4..73f84ec 100644 --- a/src/umabot/rules/__init__.py +++ b/src/umabot/rules/__init__.py @@ -3,7 +3,7 @@ from .base import Rule from .spam_detector import SpamDetector from .roleplay_limiter import RoleplayLimiter, StaticRoleplayLimiter -from .media_required import MediaRequiredRule +from .roleplay_media_required import RoleplayMediaRequiredRule from .roleplay_word_count import RoleplayWordCountRule -__all__ = ["Rule", "SpamDetector", "RoleplayLimiter", "StaticRoleplayLimiter", "MediaRequiredRule", "RoleplayWordCountRule"] +__all__ = ["Rule", "SpamDetector", "RoleplayLimiter", "StaticRoleplayLimiter", "RoleplayMediaRequiredRule", "RoleplayWordCountRule"] diff --git a/src/umabot/rules/media_required.py b/src/umabot/rules/media_required.py deleted file mode 100644 index 8158c5a..0000000 --- a/src/umabot/rules/media_required.py +++ /dev/null @@ -1,113 +0,0 @@ -"""Media requirement rule for roleplay posts.""" - -import praw.models -from .base import Rule - - -class MediaRequiredRule(Rule): - """Requires roleplay posts to have media attached.""" - - def __init__(self, config): - """Initialize the media required rule.""" - super().__init__(config) - self.roleplay_flair = "Roleplay" - - def should_remove(self, submission: praw.models.Submission) -> bool: - """Check if a roleplay post lacks required media.""" - if not submission.author: - return False - - # Check if this is a roleplay post - if not self._is_roleplay_post(submission): - return False - - # Check if the post has media - if self._has_media(submission): - return False - - # Roleplay post without media - should be removed - self.logger.info( - f"Roleplay post by {submission.author.name} removed for missing media " - f"(post ID: {submission.id})" - ) - return True - - def get_removal_message(self, submission: praw.models.Submission) -> str: - """Get the media requirement removal message.""" - return ( - f"Your roleplay post has been removed because it doesn't include any media. " - f"All roleplay posts in r/{self.config.subreddit_name} must include an image, video, " - f"or other media attachment to enhance the roleplay experience." - ) - - def _is_roleplay_post(self, submission: praw.models.Submission) -> bool: - """Check if a submission has the roleplay flair.""" - try: - # Check link flair text - if hasattr(submission, 'link_flair_text') and submission.link_flair_text: - return submission.link_flair_text.lower() == self.roleplay_flair.lower() - - # Check flair template ID (if using new flair system) - if hasattr(submission, 'link_flair_template_id') and submission.link_flair_template_id: - # You might need to map flair template IDs to names - # For now, we'll just check the text - pass - - return False - - except Exception as e: - self.logger.error(f"Error checking flair for submission {submission.id}: {e}") - return False - - def _has_media(self, submission: praw.models.Submission) -> bool: - """Check if a submission has media attached.""" - try: - # Check for image/video posts - if submission.is_video or submission.is_self: - # For self posts, check if they contain media links - if submission.is_self and submission.selftext: - # Look for common media URLs in the text - media_indicators = [ - 'imgur.com', 'i.imgur.com', 'redd.it', 'i.redd.it', - 'youtube.com', 'youtu.be', 'vimeo.com', 'gfycat.com', - 'streamable.com', 'twitter.com', 'x.com', 'tiktok.com', - 'instagram.com', 'facebook.com', 'discord.com', 'discordapp.com' - ] - - text_lower = submission.selftext.lower() - return any(indicator in text_lower for indicator in media_indicators) - return False - - # Check for link posts with media - if hasattr(submission, 'url') and submission.url: - # Check if URL points to media - url_lower = submission.url.lower() - media_extensions = ['.jpg', '.jpeg', '.png', '.gif', '.gifv', '.mp4', '.webm', '.webp'] - media_domains = [ - 'imgur.com', 'i.imgur.com', 'redd.it', 'i.redd.it', - 'youtube.com', 'youtu.be', 'vimeo.com', 'gfycat.com', - 'streamable.com', 'twitter.com', 'x.com', 'tiktok.com', - 'instagram.com', 'facebook.com' - ] - - # Check file extensions - if any(url_lower.endswith(ext) for ext in media_extensions): - return True - - # Check media domains - if any(domain in url_lower for domain in media_domains): - return True - - # Check for gallery posts - if hasattr(submission, 'is_gallery') and submission.is_gallery: - return True - - # Check for crosspost with media - if hasattr(submission, 'crosspost_parent') and submission.crosspost_parent: - return self._has_media(submission.crosspost_parent) - - return False - - except Exception as e: - self.logger.error(f"Error checking media for submission {submission.id}: {e}") - return False diff --git a/src/umabot/rules/roleplay_media_required.py b/src/umabot/rules/roleplay_media_required.py new file mode 100644 index 0000000..ec4f63f --- /dev/null +++ b/src/umabot/rules/roleplay_media_required.py @@ -0,0 +1,113 @@ +"""Roleplay media requirement rule.""" + +import praw.models +from .base import Rule + + +class RoleplayMediaRequiredRule(Rule): + """Requires roleplay posts to have media attached.""" + + def __init__(self, config): + """Initialize the media required rule.""" + super().__init__(config) + self.roleplay_flair = "Roleplay" + + def should_remove(self, submission: praw.models.Submission) -> bool: + """Check if a roleplay post lacks required media.""" + if not submission.author: + return False + + # Check if this is a roleplay post + if not self._is_roleplay_post(submission): + return False + + # Check if the post has media + if self._has_media(submission): + return False + + # Roleplay post without media - should be removed + self.logger.info( + f"Roleplay post by {submission.author.name} removed for missing media " + f"(post ID: {submission.id})" + ) + return True + + def get_removal_message(self, submission: praw.models.Submission) -> str: + """Get the media requirement removal message.""" + return ( + f"Your roleplay post has been removed because it doesn't include any media. " + f"All roleplay posts in r/{self.config.subreddit_name} must include an image, video, " + f"or other media attachment to enhance the roleplay experience." + ) + + def _is_roleplay_post(self, submission: praw.models.Submission) -> bool: + """Check if a submission has the roleplay flair.""" + try: + # Check link flair text + if hasattr(submission, 'link_flair_text') and submission.link_flair_text: + return submission.link_flair_text.lower() == self.roleplay_flair.lower() + + # Check flair template ID (if using new flair system) + if hasattr(submission, 'link_flair_template_id') and submission.link_flair_template_id: + # You might need to map flair template IDs to names + # For now, we'll just check the text + pass + + return False + + except Exception as e: + self.logger.error(f"Error checking flair for submission {submission.id}: {e}") + return False + + def _has_media(self, submission: praw.models.Submission) -> bool: + """Check if a submission has media attached.""" + try: + # Check for image/video posts + if submission.is_video or submission.is_self: + # For self posts, check if they contain media links + if submission.is_self and submission.selftext: + # Look for common media URLs in the text + media_indicators = [ + 'imgur.com', 'i.imgur.com', 'redd.it', 'i.redd.it', + 'youtube.com', 'youtu.be', 'vimeo.com', 'gfycat.com', + 'streamable.com', 'twitter.com', 'x.com', 'tiktok.com', + 'instagram.com', 'facebook.com', 'discord.com', 'discordapp.com' + ] + + text_lower = submission.selftext.lower() + return any(indicator in text_lower for indicator in media_indicators) + return False + + # Check for link posts with media + if hasattr(submission, 'url') and submission.url: + # Check if URL points to media + url_lower = submission.url.lower() + media_extensions = ['.jpg', '.jpeg', '.png', '.gif', '.gifv', '.mp4', '.webm', '.webp'] + media_domains = [ + 'imgur.com', 'i.imgur.com', 'redd.it', 'i.redd.it', + 'youtube.com', 'youtu.be', 'vimeo.com', 'gfycat.com', + 'streamable.com', 'twitter.com', 'x.com', 'tiktok.com', + 'instagram.com', 'facebook.com' + ] + + # Check file extensions + if any(url_lower.endswith(ext) for ext in media_extensions): + return True + + # Check media domains + if any(domain in url_lower for domain in media_domains): + return True + + # Check for gallery posts + if hasattr(submission, 'is_gallery') and submission.is_gallery: + return True + + # Check for crosspost with media + if hasattr(submission, 'crosspost_parent') and submission.crosspost_parent: + return self._has_media(submission.crosspost_parent) + + return False + + except Exception as e: + self.logger.error(f"Error checking media for submission {submission.id}: {e}") + return False -- cgit v1.2.3