From 570f37674434c7f3816e3949967c31407610da6c Mon Sep 17 00:00:00 2001
From: Walter Purcaro <vuolter@users.noreply.github.com>
Date: Thu, 8 Oct 2015 06:32:02 +0200
Subject: Spare improvements

---
 module/plugins/internal/Account.py   | 48 +++++++++++++++++++++++++++--------
 module/plugins/internal/Addon.py     | 49 ++++++++++++++++++++++++++++--------
 module/plugins/internal/Base.py      | 22 +++++++++-------
 module/plugins/internal/Crypter.py   |  4 +--
 module/plugins/internal/Hook.py      | 12 ++++++---
 module/plugins/internal/Hoster.py    |  4 +--
 module/plugins/internal/Plugin.py    | 12 ++++++---
 module/plugins/internal/XFSHoster.py |  5 ++--
 8 files changed, 112 insertions(+), 44 deletions(-)

(limited to 'module/plugins/internal')

diff --git a/module/plugins/internal/Account.py b/module/plugins/internal/Account.py
index 1034fec19..20ecf6afd 100644
--- a/module/plugins/internal/Account.py
+++ b/module/plugins/internal/Account.py
@@ -13,7 +13,7 @@ from module.utils import compare_time, lock
 class Account(Plugin):
     __name__    = "Account"
     __type__    = "account"
-    __version__ = "0.56"
+    __version__ = "0.57"
     __status__  = "testing"
 
     __description__ = """Base account plugin"""
@@ -21,8 +21,10 @@ class Account(Plugin):
     __authors__     = [("Walter Purcaro", "vuolter@gmail.com")]
 
 
-    LOGIN_TIMEOUT = 30 * 60  #: Relogin accounts every 30 minutes
-    AUTO_INTERVAL = True     #: Automatically adjust relogin interval
+    LOGIN_TIMEOUT = 30 * 60  #: Relogin account every 30 minutes
+    TUNE_TIMEOUT  = True     #: Automatically tune relogin interval
+
+    PERIODICAL_INTERVAL = None
 
 
     def __init__(self, manager, accounts):
@@ -38,7 +40,7 @@ class Account(Plugin):
 
         #: Callback of periodical job task
         self.cb       = None
-        self.interval = self.LOGIN_TIMEOUT
+        self.interval = None
 
         self.init()
 
@@ -50,22 +52,46 @@ class Account(Plugin):
         pass
 
 
-    def init_periodical(self, delay=0, threaded=False):
-        self.cb = self.pyload.scheduler.addJob(max(0, delay), self._periodical, [threaded], threaded=threaded)
+    def set_interval(self, value):
+        newinterval = max(0, self.PERIODICAL_INTERVAL, value)
 
+        if newinterval != value:
+            return False
 
-    def _periodical(self, threaded):
-        if self.interval < 0:
+        if newinterval != self.interval:
+            self.interval = newinterval
+
+        return True
+
+
+    def start_periodical(self, interval=None, threaded=False, delay=0):
+        if interval is not None and self.set_interval(interval) is False:
+            return False
+        else:
+            self.cb = self.pyload.scheduler.addJob(max(0, delay), self._periodical, [threaded], threaded=threaded)
+            return True
+
+
+    def restart_periodical(self, *args, **kwargs):
+        self.stop_periodical()
+        return self.start_periodical(*args, **kwargs)
+
+
+    def stop_periodical(self):
+        try:
+            return self.pyload.scheduler.removeJob(self.cb)
+        finally:
             self.cb = None
-            return
 
+
+    def _periodical(self, threaded):
         try:
             self.periodical()
 
         except Exception, e:
             self.log_error(_("Error executing periodical task: %s") % e, trace=True)
 
-        self.init_periodical(self.interval, threaded)
+        self.restart_periodical(self.interval, threaded)
 
 
     def periodical(self):
@@ -121,7 +147,7 @@ class Account(Plugin):
             self.info['login']['valid'] = True
 
             new_timeout = timestamp - self.info['login']['timestamp']
-            if self.AUTO_INTERVAL and new_timeout > self.timeout:
+            if self.TUNE_TIMEOUT and new_timeout > self.timeout:
                 self.timeout = new_timeout
 
         except Exception, e:
diff --git a/module/plugins/internal/Addon.py b/module/plugins/internal/Addon.py
index c6e7ea7b8..32344191a 100644
--- a/module/plugins/internal/Addon.py
+++ b/module/plugins/internal/Addon.py
@@ -23,7 +23,7 @@ def threaded(fn):
 class Addon(Plugin):
     __name__    = "Addon"
     __type__    = "hook"  #@TODO: Change to `addon` in 0.4.10
-    __version__ = "0.08"
+    __version__ = "0.10"
     __status__  = "testing"
 
     __threaded__ = []  #@TODO: Remove in 0.4.10
@@ -33,6 +33,9 @@ class Addon(Plugin):
     __authors__     = [("Walter Purcaro", "vuolter@gmail.com")]
 
 
+    PERIODICAL_INTERVAL = None
+
+
     def __init__(self, core, manager):
         self._init(core)
 
@@ -50,7 +53,7 @@ class Addon(Plugin):
 
         #: Callback of periodical job task, used by HookManager
         self.cb       = None
-        self.interval = 60
+        self.interval = None
 
         self.init()
         self.init_events()
@@ -83,27 +86,51 @@ class Addon(Plugin):
             self.event_list = None
 
 
-    def init_periodical(self, delay=0, threaded=False):
-        self.cb = self.pyload.scheduler.addJob(max(0, delay), self._periodical, [threaded], threaded=threaded)
+    def set_interval(self, value):
+        newinterval = max(0, self.PERIODICAL_INTERVAL, value)
 
+        if newinterval != value:
+            return False
 
-    #: Deprecated method, use `init_periodical` instead (Remove in 0.4.10)
-    def initPeriodical(self, *args, **kwargs):
-        return self.init_periodical(*args, **kwargs)
+        if newinterval != self.interval:
+            self.interval = newinterval
 
+        return True
 
-    def _periodical(self, threaded):
-        if self.interval < 0:
+
+    def start_periodical(self, interval=None, threaded=False, delay=0):
+        if interval is not None and self.set_interval(interval) is False:
+            return False
+        else:
+            self.cb = self.pyload.scheduler.addJob(max(0, delay), self._periodical, [threaded], threaded=threaded)
+            return True
+
+
+    def restart_periodical(self, *args, **kwargs):
+        self.stop_periodical()
+        return self.start_periodical(*args, **kwargs)
+
+
+    def stop_periodical(self):
+        try:
+            return self.pyload.scheduler.removeJob(self.cb)
+        finally:
             self.cb = None
-            return
 
+
+    #: Deprecated method, use `start_periodical` instead (Remove in 0.4.10)
+    def initPeriodical(self, *args, **kwargs):
+        return self.start_periodical(*args, **kwargs)
+
+
+    def _periodical(self, threaded):
         try:
             self.periodical()
 
         except Exception, e:
             self.log_error(_("Error executing periodical task: %s") % e, trace=True)
 
-        self.init_periodical(self.interval, threaded)
+        self.restart_periodical(self.interval, threaded)
 
 
     def periodical(self):
diff --git a/module/plugins/internal/Base.py b/module/plugins/internal/Base.py
index 1b2987322..46502a9d3 100644
--- a/module/plugins/internal/Base.py
+++ b/module/plugins/internal/Base.py
@@ -52,7 +52,7 @@ def check_abort(fn):
 class Base(Plugin):
     __name__    = "Base"
     __type__    = "base"
-    __version__ = "0.04"
+    __version__ = "0.05"
     __status__  = "testing"
 
     __pattern__ = r'^unmatchable$'
@@ -212,25 +212,29 @@ class Base(Plugin):
         self.log_debug("RECONNECT %s required" % ("" if reconnect else "not"),
                        "Previous wantReconnect: %s" % self.wantReconnect)
         self.wantReconnect = bool(reconnect)
+        return True
 
 
-    def set_wait(self, seconds, reconnect=None):
+    def set_wait(self, seconds, strict=False):
         """
         Set a specific wait time later used with `wait`
 
         :param seconds: wait time in seconds
         :param reconnect: True if a reconnect would avoid wait time
         """
-        wait_time  = max(int(seconds), 1)
-        wait_until = time.time() + wait_time + 1
+        wait_time = float(seconds)
 
-        self.log_debug("WAIT set to %d seconds" % wait_time,
-                       "Previous waitUntil: %f" % self.pyfile.waitUntil)
+        if wait_time < 0:
+            return False
 
-        self.pyfile.waitUntil = wait_until
+        old_wait_until = self.pyfile.waitUntil
+        new_wait_until = time.time() + wait_time + float(not strict)
 
-        if reconnect is not None:
-            self.set_reconnect(reconnect)
+        self.log_debug("WAIT set to timestamp %f" % new_wait_until,
+                       "Previous waitUntil: %f"   % old_wait_until)
+
+        self.pyfile.waitUntil = new_wait_until
+        return True
 
 
     def wait(self, seconds=None, reconnect=None):
diff --git a/module/plugins/internal/Crypter.py b/module/plugins/internal/Crypter.py
index cc1eeb5fd..db13e445c 100644
--- a/module/plugins/internal/Crypter.py
+++ b/module/plugins/internal/Crypter.py
@@ -20,8 +20,8 @@ class Crypter(Base):
     __authors__     = [("Walter Purcaro", "vuolter@gmail.com")]
 
 
-    def __init__(self, pyfile):
-        super(Crypter, self).__init__(pyfile)
+    def __init__(self, *args, **kwargs):
+        super(Crypter, self).__init__(*args, **kwargs)
 
         #: Put all packages here. It's a list of tuples like: ( name, [list of links], folder )
         self.packages = []
diff --git a/module/plugins/internal/Hook.py b/module/plugins/internal/Hook.py
index 6ead5cf0b..f1308c25b 100644
--- a/module/plugins/internal/Hook.py
+++ b/module/plugins/internal/Hook.py
@@ -6,7 +6,7 @@ from module.plugins.internal.Addon import Addon, threaded
 class Hook(Addon):
     __name__    = "Hook"
     __type__    = "hook"
-    __version__ = "0.14"
+    __version__ = "0.16"
     __status__  = "testing"
 
     __description__ = """Base hook plugin"""
@@ -16,9 +16,13 @@ class Hook(Addon):
                        ("Walter Purcaro", "vuolter@gmail.com")]
 
 
-    def __init__(self, core, manager):
-        super(Hook, self).__init__(core, manager)
-        self.init_periodical(10)
+    PERIODICAL_INTERVAL = 10
+
+
+    def __init__(self, *args, **kwargs):
+        super(Hook, self).__init__(*args, **kwargs)
+        if self.PERIODICAL_INTERVAL:
+            self.start_periodical(self.PERIODICAL_INTERVAL)
 
 
     #@TODO: Remove in 0.4.10
diff --git a/module/plugins/internal/Hoster.py b/module/plugins/internal/Hoster.py
index 96d0b86f3..09466465d 100644
--- a/module/plugins/internal/Hoster.py
+++ b/module/plugins/internal/Hoster.py
@@ -26,8 +26,8 @@ class Hoster(Base):
     __authors__     = [("Walter Purcaro", "vuolter@gmail.com")]
 
 
-    def __init__(self, pyfile):
-        super(Hoster, self).__init__(pyfile)
+    def __init__(self, *args, **kwargs):
+        super(Hoster, self).__init__(*args, **kwargs)
 
         #: Enable simultaneous processing of multiple downloads
         self.limitDL = 0     #@TODO: Change to `limit_dl` in 0.4.10
diff --git a/module/plugins/internal/Plugin.py b/module/plugins/internal/Plugin.py
index 61f219556..7bfdd588c 100644
--- a/module/plugins/internal/Plugin.py
+++ b/module/plugins/internal/Plugin.py
@@ -142,13 +142,19 @@ def which(program):
                 return exe_file
 
 
-def seconds_to_midnight(utc=None):
+def seconds_to_nexthour(strict=False):
+    now      = datetime.datetime.today()
+    nexthour = now.replace(minute=0 if strict else 1, second=0, microsecond=0) + datetime.timedelta(hours=1)
+    return (nexthour - now).seconds
+
+
+def seconds_to_midnight(utc=None, strict=False):
     if utc is None:
         now = datetime.datetime.today()
     else:
         now = datetime.datetime.utcnow() + datetime.timedelta(hours=utc)
 
-    midnight = now.replace(hour=0, minute=1, second=0, microsecond=0) + datetime.timedelta(days=1)
+    midnight = now.replace(hour=0, minute=0 if strict else 1, second=0, microsecond=0) + datetime.timedelta(days=1)
 
     return (midnight - now).seconds
 
@@ -226,7 +232,7 @@ def chunks(iterable, size):
 class Plugin(object):
     __name__    = "Plugin"
     __type__    = "plugin"
-    __version__ = "0.50"
+    __version__ = "0.51"
     __status__  = "testing"
 
     __pattern__ = r'^unmatchable$'
diff --git a/module/plugins/internal/XFSHoster.py b/module/plugins/internal/XFSHoster.py
index 99a091129..2e9cbceb2 100644
--- a/module/plugins/internal/XFSHoster.py
+++ b/module/plugins/internal/XFSHoster.py
@@ -14,7 +14,7 @@ from module.utils import html_unescape
 class XFSHoster(SimpleHoster):
     __name__    = "XFSHoster"
     __type__    = "hoster"
-    __version__ = "0.64"
+    __version__ = "0.65"
     __status__  = "testing"
 
     __pattern__ = r'^unmatchable$'
@@ -217,7 +217,8 @@ class XFSHoster(SimpleHoster):
                 m = re.search(self.WAIT_PATTERN, self.html)
                 if m is not None:
                     wait_time = int(m.group(1))
-                    self.set_wait(wait_time, False)
+                    self.set_wait(wait_time)
+                    self.set_reconnect(False)
 
                 self.handle_captcha(inputs)
                 self.wait()
-- 
cgit v1.2.3