|
3 | 3 | from datetime import datetime |
4 | 4 | from time import time |
5 | 5 | import os |
| 6 | +import json |
6 | 7 |
|
7 | 8 | from regex import Pattern, Match, split, match, search, IGNORECASE, sub |
8 | 9 | from requests import post |
|
13 | 14 | from .commands_builder import CommandsBuilder |
14 | 15 | from .data_service import BetterBotBaseDataService |
15 | 16 | from .data_builder import DataBuilder |
| 17 | +from .keyboard_utils import TopPaginationKeyboard |
16 | 18 | from .utils import ( |
17 | 19 | get_default_programming_language, |
18 | 20 | contains_all_strings, |
@@ -124,22 +126,28 @@ def top( |
124 | 126 | self, |
125 | 127 | reverse: bool = False |
126 | 128 | ) -> NoReturn: |
127 | | - """Sends users top.""" |
| 129 | + """Sends users top with pagination.""" |
128 | 130 | if self.peer_id < 2e9: |
129 | 131 | return |
130 | 132 | maximum_users = self.matched.group("maximum_users") |
131 | | - maximum_users = int(maximum_users) if maximum_users else -1 |
132 | | - users = DataBuilder.get_users_sorted_by_karma( |
133 | | - self.vk_instance, self.data_service, self.peer_id) |
134 | | - users = [i for i in users if |
135 | | - (i["karma"] != 0) or |
136 | | - ("programming_languages" in i and len(i["programming_languages"]) > 0) |
137 | | - ] |
138 | | - self.vk_instance.send_msg( |
139 | | - CommandsBuilder.build_top_users( |
| 133 | + |
| 134 | + # If specific maximum_users is requested, use old behavior without pagination |
| 135 | + if maximum_users: |
| 136 | + maximum_users = int(maximum_users) |
| 137 | + users = DataBuilder.get_users_sorted_by_karma( |
| 138 | + self.vk_instance, self.data_service, self.peer_id) |
| 139 | + users = [i for i in users if |
| 140 | + (i["karma"] != 0) or |
| 141 | + ("programming_languages" in i and len(i["programming_languages"]) > 0) |
| 142 | + ] |
| 143 | + message = CommandsBuilder.build_top_users( |
140 | 144 | users, self.data_service, reverse, |
141 | | - self.karma_enabled, maximum_users), |
142 | | - self.peer_id) |
| 145 | + self.karma_enabled, maximum_users) |
| 146 | + if message: |
| 147 | + self.vk_instance.send_msg(message, self.peer_id) |
| 148 | + else: |
| 149 | + # Use new paginated version |
| 150 | + self.top_paginated(reverse=reverse, page=0) |
143 | 151 |
|
144 | 152 | def top_langs( |
145 | 153 | self, |
@@ -436,3 +444,110 @@ def process( |
436 | 444 | if self.matched: |
437 | 445 | action() |
438 | 446 | return |
| 447 | + |
| 448 | + def process_callback( |
| 449 | + self, |
| 450 | + payload: Dict[str, Any], |
| 451 | + peer_id: int, |
| 452 | + from_id: int, |
| 453 | + event_id: str, |
| 454 | + user: BetterUser |
| 455 | + ) -> NoReturn: |
| 456 | + """Process callback button events |
| 457 | + |
| 458 | + :param payload: Callback payload data |
| 459 | + :param peer_id: chat ID |
| 460 | + :param from_id: user ID |
| 461 | + :param event_id: callback event ID |
| 462 | + :param user: user object |
| 463 | + """ |
| 464 | + self.peer_id = peer_id |
| 465 | + self.from_id = from_id |
| 466 | + self.karma_enabled = peer_id in config.CHATS_KARMA_WHITELIST |
| 467 | + self.current_user = user |
| 468 | + |
| 469 | + if from_id < 0: |
| 470 | + return |
| 471 | + |
| 472 | + try: |
| 473 | + # Parse payload if it's a string |
| 474 | + if isinstance(payload, str): |
| 475 | + payload = json.loads(payload) |
| 476 | + |
| 477 | + action = payload.get("action") |
| 478 | + |
| 479 | + if action == "paginate": |
| 480 | + self.handle_top_pagination(payload, event_id) |
| 481 | + elif action == "page_info": |
| 482 | + # Just acknowledge the page info button click |
| 483 | + self.vk_instance.send_callback_answer(event_id, peer_id) |
| 484 | + |
| 485 | + except Exception as e: |
| 486 | + print(f"Error processing callback: {e}") |
| 487 | + # Send empty callback answer to acknowledge the button press |
| 488 | + self.vk_instance.send_callback_answer(event_id, peer_id) |
| 489 | + |
| 490 | + def handle_top_pagination( |
| 491 | + self, |
| 492 | + payload: Dict[str, Any], |
| 493 | + event_id: str |
| 494 | + ) -> NoReturn: |
| 495 | + """Handle pagination for top command""" |
| 496 | + command = payload.get("command", "top") |
| 497 | + page = payload.get("page", 0) |
| 498 | + reverse = payload.get("reverse", False) |
| 499 | + |
| 500 | + # Execute the appropriate top command with pagination |
| 501 | + if command == "top": |
| 502 | + self.top_paginated(reverse=reverse, page=page) |
| 503 | + elif command == "bottom": |
| 504 | + self.top_paginated(reverse=True, page=page) |
| 505 | + elif command == "people": |
| 506 | + self.top_paginated(reverse=reverse, page=page) |
| 507 | + |
| 508 | + # Acknowledge the callback |
| 509 | + self.vk_instance.send_callback_answer(event_id, self.peer_id) |
| 510 | + |
| 511 | + def top_paginated( |
| 512 | + self, |
| 513 | + reverse: bool = False, |
| 514 | + page: int = 0 |
| 515 | + ) -> NoReturn: |
| 516 | + """Sends paginated users top with callback buttons.""" |
| 517 | + if self.peer_id < 2e9: |
| 518 | + return |
| 519 | + |
| 520 | + users = DataBuilder.get_users_sorted_by_karma( |
| 521 | + self.vk_instance, self.data_service, self.peer_id) |
| 522 | + users = [i for i in users if |
| 523 | + (i["karma"] != 0) or |
| 524 | + ("programming_languages" in i and len(i["programming_languages"]) > 0) |
| 525 | + ] |
| 526 | + |
| 527 | + if reverse: |
| 528 | + users = list(reversed(users)) |
| 529 | + |
| 530 | + # Calculate pagination |
| 531 | + pagination_info = TopPaginationKeyboard.calculate_pagination(len(users)) |
| 532 | + total_pages = pagination_info["total_pages"] |
| 533 | + |
| 534 | + # Ensure page is within valid range |
| 535 | + page = max(0, min(page, total_pages - 1)) |
| 536 | + |
| 537 | + # Get users for current page |
| 538 | + page_users = TopPaginationKeyboard.get_page_users(users, page) |
| 539 | + |
| 540 | + # Build message |
| 541 | + command_type = "bottom" if reverse else "top" |
| 542 | + message = CommandsBuilder.build_top_users( |
| 543 | + page_users, self.data_service, False, |
| 544 | + self.karma_enabled, -1) |
| 545 | + |
| 546 | + if message: |
| 547 | + # Create pagination keyboard |
| 548 | + keyboard = TopPaginationKeyboard.create_pagination_keyboard( |
| 549 | + page, total_pages, command_type, reverse) |
| 550 | + |
| 551 | + self.vk_instance.send_msg_with_keyboard(message, self.peer_id, keyboard) |
| 552 | + else: |
| 553 | + self.vk_instance.send_msg("Пользователи не найдены.", self.peer_id) |
0 commit comments