jenkins-bot has submitted this change. ( 
https://gerrit.wikimedia.org/r/c/pywikibot/core/+/774015 )

Change subject: [IMPR] Handle ratelimit with purgepages()
......................................................................

[IMPR] Handle ratelimit with purgepages()

If a ratelimit for purge action exceeded the pages aren't purged
until the limit is fallen below the limit. This change handles those
warnings and retries the request.

- add a new _default_warning_handler to handle purge rate limits.
  It return True to retry the request, False to resume and None if
  the warning is not handled.
- change _handle_warnings and return True to retry request
  and False to resume. Call _default_warning_handler if
  _warning_handler did not handle it already

Bug: T152597
Change-Id: Iac4f4d0383e2b66e03e8fa379f2754fdece6931e
---
M pywikibot/data/api.py
1 file changed, 57 insertions(+), 20 deletions(-)

Approvals:
  D3r1ck01: Looks good to me, approved
  jenkins-bot: Verified



diff --git a/pywikibot/data/api.py b/pywikibot/data/api.py
index 70c7f9c..c04e093 100644
--- a/pywikibot/data/api.py
+++ b/pywikibot/data/api.py
@@ -1585,27 +1585,63 @@
                 return True
         return False

-    def _handle_warnings(self, result) -> None:
-        if 'warnings' in result:
-            for mod, warning in result['warnings'].items():
-                if mod == 'info':
-                    continue
-                if '*' in warning:
-                    text = warning['*']
-                elif 'html' in warning:
-                    # bug T51978
-                    text = warning['html']['*']
-                else:
-                    pywikibot.warning(
-                        'API warning ({}) of unknown format: {}'.
-                        format(mod, warning))
-                    continue
-                # multiple warnings are in text separated by a newline
-                for single_warning in text.splitlines():
-                    if (not callable(self._warning_handler)
-                            or not self._warning_handler(mod, single_warning)):
+    def _handle_warnings(self, result: Dict[str, Any]) -> bool:
+        """Handle warnings; return True to retry request, False to resume.
+
+        .. versionchanged:: 7.2
+           Return True to retry the current request and Falso to resume.
+        """
+        retry = False
+        if 'warnings' not in result:
+            return retry
+
+        for mod, warning in result['warnings'].items():
+            if mod == 'info':
+                continue
+            if '*' in warning:
+                text = warning['*']
+            elif 'html' in warning:
+                # bug T51978
+                text = warning['html']['*']
+            else:
+                pywikibot.warning('API warning ({}) of unknown format: {}'
+                                  .format(mod, warning))
+                continue
+
+            # multiple warnings are in text separated by a newline
+            for single_warning in text.splitlines():
+                if (not callable(self._warning_handler)
+                        or not self._warning_handler(mod, single_warning)):
+                    handled = self._default_warning_handler(mod,
+                                                            single_warning)
+                    if handled is None:
                         pywikibot.warning('API warning ({}): {}'
                                           .format(mod, single_warning))
+                    else:
+                        retry = retry or handled
+        return retry
+
+    def _default_warning_handler(self, mode: str, msg: str) -> Optional[bool]:
+        """A default warning handler to handle specific warnings.
+
+        Return True to retry the request, False to resume and None if
+        the warning is not handled.
+
+        .. versionadded:: 7.2
+        """
+        warnings = {
+            'purge': ("You've exceeded your rate limit. "
+                      'Please wait some time and try again.',
+                      '_ratelimited', True),
+        }
+        warning, handler, retry = warnings.get(mode, (None, None, None))
+        if handler and msg == warning:
+            # Only show the first warning part
+            pywikibot.warning(msg.split('.')[0] + '.')
+            # call the handler
+            getattr(self, handler)()
+            return retry
+        return None

     def _logged_in(self, code) -> bool:
         """Check whether user is logged in.
@@ -1771,7 +1807,8 @@
             if self._userinfo_query(result):
                 continue

-            self._handle_warnings(result)
+            if self._handle_warnings(result):
+                continue

             if 'error' not in result:
                 return result

--
To view, visit https://gerrit.wikimedia.org/r/c/pywikibot/core/+/774015
To unsubscribe, or for help writing mail filters, visit 
https://gerrit.wikimedia.org/r/settings

Gerrit-Project: pywikibot/core
Gerrit-Branch: master
Gerrit-Change-Id: Iac4f4d0383e2b66e03e8fa379f2754fdece6931e
Gerrit-Change-Number: 774015
Gerrit-PatchSet: 3
Gerrit-Owner: Xqt <[email protected]>
Gerrit-Reviewer: D3r1ck01 <[email protected]>
Gerrit-Reviewer: Lokal Profil <[email protected]>
Gerrit-Reviewer: jenkins-bot
Gerrit-MessageType: merged
_______________________________________________
Pywikibot-commits mailing list -- [email protected]
To unsubscribe send an email to [email protected]

Reply via email to