import re import config from response import generate_response from fediverse_factory import get_fediverse_service from fediverse_types import FediverseNotification, NotificationType, Visibility from custom_types import ParsedNotification def parse_notification(notification: FediverseNotification, fediverse_service=None): '''Parses any notifications received by the bot and sends any commands to generate_response()''' if fediverse_service is None: fediverse_service = get_fediverse_service() # We get the type of notification to filter the ones that we actually want # to parse if notification.type not in (NotificationType.MENTION, NotificationType.REPLY): return # Ignore anything that isn't a mention # Return early if no post attached if not notification.post: return # We want the visibility to be related to the type that was received (so if # people don't want to dump a bunch of notes on home they don't have to) if notification.post.visibility != Visibility.SPECIFIED: visibility = Visibility.HOME else: visibility = Visibility.SPECIFIED # Get the full Activitypub ID of the user full_user = notification.user.full_handle note_text = notification.post.text note_id = notification.post.id note = note_text.strip().lower() if note_text else "" # Check for both short and fully-qualified name mentions username_variants = [ config.USER, f'@{config.USER.split("@")[1]}' ] # Make sure the notification text explicitly mentions the bot if not any(variant in note for variant in username_variants): return None # Find command and arguments after the mention # Removes all mentions # regex = mentions that start with @ and may contain @domain cleaned_text = re.sub(r"@\w+(?:@\S+)?", "", note).strip() parts = cleaned_text.split() command = parts[0].lower() if parts else None arguments = parts[1:] if len(parts) > 1 else [] # Create ParsedNotification object for the new response system parsed_notification: ParsedNotification = { 'author': full_user, 'command': command, 'arguments': arguments, 'note_obj': { 'id': note_id, 'text': note_text, 'files': [{'url': f.url} for f in notification.post.files] if notification.post.files else [] } } # Generate response using the new system response = generate_response(parsed_notification) if not response: return # Handle attachment URLs (convert to file IDs if needed) file_ids = response['attachment_urls'] if response['attachment_urls'] else None fediverse_service.create_post( text=response['message'], reply_to_id=note_id, visibility=visibility, file_ids=file_ids #visible_user_ids=[] #todo: write actual visible users ids so pleromers can use the bot privately )