diff options
| author | 2012-09-18 17:59:50 +0200 | |
|---|---|---|
| committer | 2012-09-18 17:59:50 +0200 | |
| commit | 6130a2377ca6754fee88773097ce220abef1aa47 (patch) | |
| tree | 76bea0d76393100fcf393c164c96d34f286aba7a /module/plugins/hooks | |
| parent | Added DuckcryptInfo decrypter, smaller fixes (diff) | |
| parent | dropdowns in navbar (diff) | |
| download | pyload-6130a2377ca6754fee88773097ce220abef1aa47.tar.xz | |
merged stable into default
Diffstat (limited to 'module/plugins/hooks')
29 files changed, 0 insertions, 3357 deletions
| diff --git a/module/plugins/hooks/AlldebridCom.py b/module/plugins/hooks/AlldebridCom.py deleted file mode 100644 index f9657ed8c..000000000 --- a/module/plugins/hooks/AlldebridCom.py +++ /dev/null @@ -1,39 +0,0 @@ -# -*- coding: utf-8 -*- - -# should be working - -from module.network.RequestFactory import getURL -from module.plugins.internal.MultiHoster import MultiHoster - -class AlldebridCom(MultiHoster): -    __name__ = "AlldebridCom" -    __version__ = "0.11" -    __type__ = "hook" - -    __config__ = [("activated", "bool", "Activated", "False"), -                  ("https", "bool", "Enable HTTPS", "False"), -                  ("hosterListMode", "all;listed;unlisted", "Use for hosters (if supported)", "all"), -                  ("hosterList", "str", "Hoster list (comma separated)", "")] - -    __description__ = """Real-Debrid.com hook plugin""" -    __author_name__ = ("Andy, Voigt") -    __author_mail__ = ("spamsales@online.de") - -    replacements = [("freakshare.net", "freakshare.com")] - -    def getHoster(self): -        https = "https" if self.getConfig("https") else "http" -        page = getURL(https + "://www.alldebrid.com/api.php?action=get_host").replace("\"","").strip() -         -        hosters = set([x.strip() for x in page.split(",") if x.strip()]) -         -        configMode = self.getConfig('hosterListMode') -        if configMode in ("listed", "unlisted"): -            configList = set(self.getConfig('hosterList').strip().lower().replace('|',',').replace(';',',').split(',')) -            configList.discard(u'') -            if configMode == "listed": -                hosters &= configList -            else: -                hosters -= configList -         -        return list(hosters) diff --git a/module/plugins/hooks/BypassCaptcha.py b/module/plugins/hooks/BypassCaptcha.py deleted file mode 100644 index 24ad17dd8..000000000 --- a/module/plugins/hooks/BypassCaptcha.py +++ /dev/null @@ -1,143 +0,0 @@ -# -*- coding: utf-8 -*- -""" -    This program is free software; you can redistribute it and/or modify -    it under the terms of the GNU General Public License as published by -    the Free Software Foundation; either version 3 of the License, -    or (at your option) any later version. - -    This program is distributed in the hope that it will be useful, -    but WITHOUT ANY WARRANTY; without even the implied warranty of -    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. -    See the GNU General Public License for more details. - -    You should have received a copy of the GNU General Public License -    along with this program; if not, see <http://www.gnu.org/licenses/>. - -    @author: RaNaN, Godofdream, zoidberg -""" - -from thread import start_new_thread -from pycurl import FORM_FILE, LOW_SPEED_TIME - -from module.network.RequestFactory import getURL, getRequest -from module.network.HTTPRequest import BadHeader - -from module.plugins.Hook import Hook - -PYLOAD_KEY = "4f771155b640970d5607f919a615bdefc67e7d32" - -class BypassCaptchaException(Exception): -    def __init__(self, err): -        self.err = err - -    def getCode(self): -        return self.err - -    def __str__(self): -        return "<BypassCaptchaException %s>" % self.err - -    def __repr__(self): -        return "<BypassCaptchaException %s>" % self.err - -class BypassCaptcha(Hook): -    __name__ = "BypassCaptcha" -    __version__ = "0.03" -    __description__ = """send captchas to BypassCaptcha.com""" -    __config__ = [("activated", "bool", "Activated", True), -                  ("force", "bool", "Force BC even if client is connected", False), -                  ("passkey", "password", "Passkey", "")] -    __author_name__ = ("RaNaN", "Godofdream", "zoidberg") -    __author_mail__ = ("RaNaN@pyload.org", "soilfcition@gmail.com", "zoidberg@mujmail.cz") - -    SUBMIT_URL = "http://bypasscaptcha.com/upload.php" -    RESPOND_URL = "http://bypasscaptcha.com/check_value.php" -    GETCREDITS_URL = "http://bypasscaptcha.com/ex_left.php" - -    def setup(self): -        self.info = {} - -    def getCredits(self): -        response = getURL(self.GETCREDITS_URL, -                      post = {"key": self.getConfig("passkey")} -                      ) -                                                                          -        data = dict([x.split(' ',1) for x in response.splitlines()]) -        return int(data['Left']) -         - -    def submit(self, captcha, captchaType="file", match=None): -        req = getRequest() - -        #raise timeout threshold -        req.c.setopt(LOW_SPEED_TIME, 80) - -        try: -            response = req.load(self.SUBMIT_URL,  -                            post={"vendor_key": PYLOAD_KEY, -                                  "key": self.getConfig("passkey"), -                                  "gen_task_id": "1", -                                  "file": (FORM_FILE, captcha)}, -                            multipart=True) -        finally: -            req.close() - -        data = dict([x.split(' ',1) for x in response.splitlines()]) -        if not data or "Value" not in data: -            raise BypassCaptchaException(response) -             -        result = data['Value'] -        ticket = data['TaskId'] -        self.logDebug("result %s : %s" % (ticket,result)) - -        return ticket, result - -    def respond(self, ticket, success): -        try: -            response = getURL(self.RESPOND_URL,  -                              post={"task_id": ticket, -                                    "key": self.getConfig("passkey"), -                                    "cv": 1 if success else 0} -                              ) -        except BadHeader, e: -            self.logError("Could not send response.", str(e)) - -    def newCaptchaTask(self, task): -        if "service" in task.data: -            return False -         -        if not task.isTextual(): -            return False - -        if not self.getConfig("passkey"): -            return False - -        if self.core.isClientConnected() and not self.getConfig("force"): -            return False - -        if self.getCredits() > 0: -            task.handler.append(self) -            task.data['service'] = self.__name__ -            task.setWaiting(100) -            start_new_thread(self.processCaptcha, (task,)) - -        else: -            self.logInfo("Your %s account has not enough credits" % self.__name__) - -    def captchaCorrect(self, task): -        if task.data['service'] == self.__name__ and "ticket" in task.data: -            self.respond(task.data["ticket"], True) - -    def captchaInvalid(self, task): -        if task.data['service'] == self.__name__ and "ticket" in task.data: -            self.respond(task.data["ticket"], False) - -    def processCaptcha(self, task): -        c = task.captchaFile -        try: -            ticket, result = self.submit(c) -        except BypassCaptchaException, e: -            task.error = e.getCode() -            return - -        task.data["ticket"] = ticket -        task.setResult(result)
\ No newline at end of file diff --git a/module/plugins/hooks/CaptchaBrotherhood.py b/module/plugins/hooks/CaptchaBrotherhood.py deleted file mode 100644 index a22a5ee1d..000000000 --- a/module/plugins/hooks/CaptchaBrotherhood.py +++ /dev/null @@ -1,169 +0,0 @@ -# -*- coding: utf-8 -*- -""" -    This program is free software; you can redistribute it and/or modify -    it under the terms of the GNU General Public License as published by -    the Free Software Foundation; either version 3 of the License, -    or (at your option) any later version. - -    This program is distributed in the hope that it will be useful, -    but WITHOUT ANY WARRANTY; without even the implied warranty of -    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. -    See the GNU General Public License for more details. - -    You should have received a copy of the GNU General Public License -    along with this program; if not, see <http://www.gnu.org/licenses/>. - -    @author: mkaay, RaNaN, zoidberg -""" -from __future__ import with_statement - -from thread import start_new_thread - -import pycurl -import StringIO -from urllib import urlencode -from time import sleep -import Image - -from module.network.RequestFactory import getURL, getRequest -from module.network.HTTPRequest import BadHeader -from module.plugins.Hook import Hook - -class CaptchaBrotherhoodException(Exception): -    def __init__(self, err): -        self.err = err - -    def getCode(self): -        return self.err - -    def __str__(self): -        return "<CaptchaBrotherhoodException %s>" % self.err - -    def __repr__(self): -        return "<CaptchaBrotherhoodException %s>" % self.err - -class CaptchaBrotherhood(Hook): -    __name__ = "CaptchaBrotherhood" -    __version__ = "0.03" -    __description__ = """send captchas to CaptchaBrotherhood.com""" -    __config__ = [("activated", "bool", "Activated", False), -                  ("username", "str", "Username", ""), -                  ("force", "bool", "Force CT even if client is connected", False), -                  ("passkey", "password", "Password", ""),] -    __author_name__ = ("RaNaN", "zoidberg") -    __author_mail__ = ("RaNaN@pyload.org", "zoidberg@mujmail.cz") -     -    API_URL = "http://ocrhood.gazcad.com/" - -    def setup(self): -        self.info = {} - -    def getCredits(self): -        response = getURL(self.API_URL + "askCredits.aspx", -                          get = {"username": self.getConfig("username"), -                                 "password": self.getConfig("passkey")}) -        if not response.startswith("OK"): -            raise CaptchaBrotherhoodException(response) -        else: -            credits = int(response[3:]) -            self.logInfo(_("%d credits left") % credits) -            self.info["credits"] = credits -            return credits - -    def submit(self, captcha, captchaType="file", match=None):                -        try: -            img = Image.open(captcha) -            output = StringIO.StringIO() -            self.logDebug("CAPTCHA IMAGE", img, img.format, img.mode) -            if img.format in ("GIF", "JPEG"): -                img.save(output, img.format) -            else:     -                if img.mode != "RGB": -                    img = img.convert("RGB") -                img.save(output, "JPEG") -            data = output.getvalue() -            output.close() -        except Exception, e: -            raise CaptchaBrotherhoodException("Reading or converting captcha image failed: %s" % e) -         -        req = getRequest() - -        url = "%ssendNewCaptcha.aspx?%s" % (self.API_URL,  -                   urlencode({"username": self.getConfig("username"), -                              "password": self.getConfig("passkey"), -                              "captchaSource": "pyLoad", -                              "timeout": "80"}) -                   ) - -        req.c.setopt(pycurl.URL, url) -        req.c.setopt(pycurl.POST, 1) -        req.c.setopt(pycurl.POSTFIELDS, data) -        req.c.setopt(pycurl.HTTPHEADER, [ "Content-Type: text/html" ])         - -        try: -            req.c.perform() -            response = req.getResponse() -        except Exception, e: -            raise CaptchaBrotherhoodException("Submit captcha image failed") -             -        req.close() - -        if not response.startswith("OK"): -            raise CaptchaBrotherhoodException(response[1]) -        -        ticket = response[3:] -         -        for i in range(15): -            sleep(5) -            response = self.get_api("askCaptchaResult", ticket) -            if response.startswith("OK-answered"): -                return ticket, response[12:]  - -        raise CaptchaBrotherhoodException("No solution received in time") - -    def get_api(self, api, ticket): -        response = getURL("%s%s.aspx" % (self.API_URL, api),  -                          get={"username": self.getConfig("username"), -                               "password": self.getConfig("passkey"), -                               "captchaID": ticket} -                          ) -        if not response.startswith("OK"): -            raise CaptchaBrotherhoodException("Unknown response: %s" % response) -         -        return response - -    def newCaptchaTask(self, task): -        if "service" in task.data: -            return False -             -        if not task.isTextual(): -            return False - -        if not self.getConfig("username") or not self.getConfig("passkey"): -            return False - -        if self.core.isClientConnected() and not self.getConfig("force"): -            return False - -        if self.getCredits() > 10: -            task.handler.append(self) -            task.data['service'] = self.__name__ -            task.setWaiting(100) -            start_new_thread(self.processCaptcha, (task,)) -        else: -            self.logInfo("Your CaptchaBrotherhood Account has not enough credits") - -    def captchaInvalid(self, task): -        if task.data['service'] == self.__name__ and "ticket" in task.data: -            response = self.get_api("complainCaptcha", task.data['ticket']) - -    def processCaptcha(self, task): -        c = task.captchaFile -        try: -            ticket, result = self.submit(c) -        except CaptchaBrotherhoodException, e: -            task.error = e.getCode() -            return - -        task.data["ticket"] = ticket -        task.setResult(result)
\ No newline at end of file diff --git a/module/plugins/hooks/CaptchaTrader.py b/module/plugins/hooks/CaptchaTrader.py deleted file mode 100644 index 2b8a50a8e..000000000 --- a/module/plugins/hooks/CaptchaTrader.py +++ /dev/null @@ -1,159 +0,0 @@ -# -*- coding: utf-8 -*- -""" -    This program is free software; you can redistribute it and/or modify -    it under the terms of the GNU General Public License as published by -    the Free Software Foundation; either version 3 of the License, -    or (at your option) any later version. - -    This program is distributed in the hope that it will be useful, -    but WITHOUT ANY WARRANTY; without even the implied warranty of -    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. -    See the GNU General Public License for more details. - -    You should have received a copy of the GNU General Public License -    along with this program; if not, see <http://www.gnu.org/licenses/>. - -    @author: mkaay, RaNaN -""" - -try: -    from json import loads -except ImportError: -    from simplejson import loads - -from thread import start_new_thread -from pycurl import FORM_FILE, LOW_SPEED_TIME - -from module.network.RequestFactory import getURL, getRequest -from module.network.HTTPRequest import BadHeader - -from module.plugins.Hook import Hook - -PYLOAD_KEY = "9f65e7f381c3af2b076ea680ae96b0b7" - -class CaptchaTraderException(Exception): -    def __init__(self, err): -        self.err = err - -    def getCode(self): -        return self.err - -    def __str__(self): -        return "<CaptchaTraderException %s>" % self.err - -    def __repr__(self): -        return "<CaptchaTraderException %s>" % self.err - -class CaptchaTrader(Hook): -    __name__ = "CaptchaTrader" -    __version__ = "0.14" -    __description__ = """send captchas to captchatrader.com""" -    __config__ = [("activated", "bool", "Activated", True), -                  ("username", "str", "Username", ""), -                  ("force", "bool", "Force CT even if client is connected", False), -                  ("passkey", "password", "Password", ""),] -    __author_name__ = ("RaNaN") -    __author_mail__ = ("RaNaN@pyload.org") - -    SUBMIT_URL = "http://api.captchatrader.com/submit" -    RESPOND_URL = "http://api.captchatrader.com/respond" -    GETCREDITS_URL = "http://api.captchatrader.com/get_credits/username:%(user)s/password:%(password)s/" - -    def setup(self): -        self.info = {} - -    def getCredits(self): -        json = getURL(CaptchaTrader.GETCREDITS_URL % {"user": self.getConfig("username"), -                                                           "password": self.getConfig("passkey")}) -        response = loads(json) -        if response[0] < 0: -            raise CaptchaTraderException(response[1]) -        else: -            self.logInfo(_("%s credits left") % response[1]) -            self.info["credits"] = response[1] -            return response[1] - -    def submit(self, captcha, captchaType="file", match=None): -        if not PYLOAD_KEY: -            raise CaptchaTraderException("No API Key Specified!") - -        #if type(captcha) == str and captchaType == "file": -        #    raise CaptchaTraderException("Invalid Type") -        assert captchaType in ("file", "url-jpg", "url-jpeg", "url-png", "url-bmp") - -        req = getRequest() - -        #raise timeout threshold -        req.c.setopt(LOW_SPEED_TIME, 80) - -        try: -            json = req.load(CaptchaTrader.SUBMIT_URL, post={"api_key": PYLOAD_KEY, -                                                           "username": self.getConfig("username"), -                                                           "password": self.getConfig("passkey"), -                                                           "value": (FORM_FILE, captcha), -                                                           "type": captchaType}, multipart=True) -        finally: -            req.close() - -        response = loads(json) -        if response[0] < 0: -            raise CaptchaTraderException(response[1]) - -        ticket = response[0] -        result = response[1] -        self.logDebug("result %s : %s" % (ticket,result)) - -        return ticket, result - -    def respond(self, ticket, success): -        try: -            json = getURL(CaptchaTrader.RESPOND_URL, post={"is_correct": 1 if success else 0, -                                                            "username": self.getConfig("username"), -                                                            "password": self.getConfig("passkey"), -                                                            "ticket": ticket}) - -            response = loads(json) -            if response[0] < 0: -                raise CaptchaTraderException(response[1]) - -        except BadHeader, e: -            self.logError(_("Could not send response."), str(e)) - -    def newCaptchaTask(self, task): -        if not task.isTextual(): -            return False - -        if not self.getConfig("username") or not self.getConfig("passkey"): -            return False - -        if self.core.isClientConnected() and not self.getConfig("force"): -            return False - -        if self.getCredits() > 10: -            task.handler.append(self) -            task.setWaiting(100) -            start_new_thread(self.processCaptcha, (task,)) - -        else: -            self.logInfo(_("Your CaptchaTrader Account has not enough credits")) - -    def captchaCorrect(self, task): -        if "ticket" in task.data: -            ticket = task.data["ticket"] -            self.respond(ticket, True) - -    def captchaInvalid(self, task): -        if "ticket" in task.data: -            ticket = task.data["ticket"] -            self.respond(ticket, False) - -    def processCaptcha(self, task): -        c = task.captchaFile -        try: -            ticket, result = self.submit(c) -        except CaptchaTraderException, e: -            task.error = e.getCode() -            return - -        task.data["ticket"] = ticket -        task.setResult(result) diff --git a/module/plugins/hooks/Checksum.py b/module/plugins/hooks/Checksum.py deleted file mode 100644 index cb6f4bfe8..000000000 --- a/module/plugins/hooks/Checksum.py +++ /dev/null @@ -1,123 +0,0 @@ -# -*- coding: utf-8 -*- - -""" -    This program is free software; you can redistribute it and/or modify -    it under the terms of the GNU General Public License as published by -    the Free Software Foundation; either version 3 of the License, -    or (at your option) any later version. - -    This program is distributed in the hope that it will be useful, -    but WITHOUT ANY WARRANTY; without even the implied warranty of -    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. -    See the GNU General Public License for more details. - -    You should have received a copy of the GNU General Public License -    along with this program; if not, see <http://www.gnu.org/licenses/>. - -    @author: zoidberg -""" -from __future__ import with_statement -import hashlib, zlib -from os.path import getsize, isfile - -from module.utils import save_join, fs_encode -from module.plugins.Hook import Hook - -def computeChecksum(local_file, algorithm):  -    if algorithm in getattr(hashlib, "algorithms", ("md5", "sha1", "sha224", "sha256", "sha384", "sha512")): -        h = getattr(hashlib, algorithm)() -        chunk_size = 128 * h.block_size -         -        with open(local_file, 'rb') as f:  -            for chunk in iter(lambda: f.read(chunk_size), ''):  -                 h.update(chunk) -         -        return h.hexdigest() -          -    elif algorithm in ("adler32", "crc32"): -        hf = getattr(zlib, algorithm) -        last = 0 -         -        with open(local_file, 'rb') as f:  -            for chunk in iter(lambda: f.read(8192), ''):  -                last = hf(chunk, last) -         -        return "%x" % last -     -    else: -        return None       - -class Checksum(Hook): -    __name__ = "Checksum" -    __version__ = "0.05" -    __description__ = "Verify downloaded file size and checksum (enable in general preferences)" -    __config__ = [("activated", "bool", "Activated", True), -                  ("action", "fail;retry;nothing", "What to do if check fails?", "retry"), -                  ("max_tries", "int", "Number of retries", 2)] -    __author_name__ = ("zoidberg") -    __author_mail__ = ("zoidberg@mujmail.cz") -     -    def setup(self):     -        self.algorithms = sorted(getattr(hashlib, "algorithms", ("md5", "sha1", "sha224", "sha256", "sha384", "sha512")), reverse = True) -        self.algorithms.extend(["crc32", "adler32"]) -         -        if not self.config['general']['checksum']: -            self.logInfo("Checksum validation is disabled in general configuration")                                   -              -    def downloadFinished(self, pyfile): -        """  -        Compute checksum for the downloaded file and compare it with the hash provided by the hoster. -        pyfile.plugin.check_data should be a dictionary which can contain: -        a) if known, the exact filesize in bytes (e.g. "size": 123456789) -        b) hexadecimal hash string with algorithm name as key (e.g. "md5": "d76505d0869f9f928a17d42d66326307")     -        """                 -        if hasattr(pyfile.plugin, "check_data") and (isinstance(pyfile.plugin.check_data, dict)): -            data = pyfile.plugin.check_data.copy()         -        elif hasattr(pyfile.plugin, "api_data") and (isinstance(pyfile.plugin.api_data, dict)): -            data = pyfile.plugin.api_data.copy()   -        else: -            return  -         -        self.logDebug(data)        -         -        download_folder = self.config['general']['download_folder'] -        local_file = fs_encode(save_join(download_folder, pyfile.package().folder, pyfile.name)) -         -        if not isfile(local_file): -            self.checkFailed(pyfile, "File does not exist")   -         -        # validate file size -        if "size" in data: -            api_size = int(data['size']) -            file_size = getsize(local_file) -            if api_size != file_size: -                self.logWarning("File %s has incorrect size: %d B (%d expected)" % (pyfile.name, file_size, api_size)) -                self.checkFailed(pyfile, "Incorrect file size") -            del data['size'] -                 -        # validate checksum -        if data and self.config['general']['checksum']:                                                        -            if "checksum" in data: -                data['md5'] = data['checksum'] -             -            for key in self.algorithms: -                if key in data:  -                    checksum = computeChecksum(local_file, key.replace("-","").lower())                     -                    if checksum: -                        if checksum == data[key]: -                            self.logInfo('File integrity of "%s" verified by %s checksum (%s).' % (pyfile.name, key.upper(), checksum)) -                            return -                        else: -                            self.logWarning("%s checksum for file %s does not match (%s != %s)" % (key.upper(), pyfile.name, checksum, data[key]))     -                            self.checkFailed(pyfile, "Checksums do not match") -                    else: -                        self.logWarning("Unsupported hashing algorithm: %s" % key.upper())   -            else: -                self.logWarning("Unable to validate checksum for file %s" % (pyfile.name)) -     -    def checkFailed(self, pyfile, msg): -        action = self.getConfig("action") -        if action == "fail": -            pyfile.plugin.fail(reason = msg) -        elif action == "retry": -            pyfile.plugin.retry(reason = msg, max_tries = self.getConfig("max_tries"))
\ No newline at end of file diff --git a/module/plugins/hooks/ClickAndLoad.py b/module/plugins/hooks/ClickAndLoad.py deleted file mode 100644 index 97e5cd57d..000000000 --- a/module/plugins/hooks/ClickAndLoad.py +++ /dev/null @@ -1,89 +0,0 @@ -# -*- coding: utf-8 -*- - -""" -    This program is free software; you can redistribute it and/or modify -    it under the terms of the GNU General Public License as published by -    the Free Software Foundation; either version 3 of the License, -    or (at your option) any later version. - -    This program is distributed in the hope that it will be useful, -    but WITHOUT ANY WARRANTY; without even the implied warranty of -    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. -    See the GNU General Public License for more details. - -    You should have received a copy of the GNU General Public License -    along with this program; if not, see <http://www.gnu.org/licenses/>. -     -    @author: RaNaN -    @interface-version: 0.2 -""" - -import socket -import thread - -from module.plugins.Hook import Hook - -class ClickAndLoad(Hook): -    __name__ = "ClickAndLoad" -    __version__ = "0.2" -    __description__ = """Gives abillity to use jd's click and load. depends on webinterface""" -    __config__ = [("activated", "bool", "Activated", "True"), -                  ("extern", "bool", "Allow external link adding", "False")] -    __author_name__ = ("RaNaN", "mkaay") -    __author_mail__ = ("RaNaN@pyload.de", "mkaay@mkaay.de") - -    def coreReady(self): -        self.port = int(self.core.config['webinterface']['port']) -        if self.core.config['webinterface']['activated']: -            try: -                if self.getConfig("extern"): -                    ip = "0.0.0.0" -                else: -                    ip = "127.0.0.1" - -                thread.start_new_thread(proxy, (self, ip, self.port, 9666)) -            except: -                self.log.error("ClickAndLoad port already in use.") - - -def proxy(self, *settings): -    thread.start_new_thread(server, (self,) + settings) -    lock = thread.allocate_lock() -    lock.acquire() -    lock.acquire() - - -def server(self, *settings): -    try: -        dock_socket = socket.socket(socket.AF_INET, socket.SOCK_STREAM) -        dock_socket.bind((settings[0], settings[2])) -        dock_socket.listen(5) -        while True: -            client_socket = dock_socket.accept()[0] -            server_socket = socket.socket(socket.AF_INET, socket.SOCK_STREAM) -            server_socket.connect(("127.0.0.1", settings[1])) -            thread.start_new_thread(forward, (client_socket, server_socket)) -            thread.start_new_thread(forward, (server_socket, client_socket)) -    except socket.error, e: -        if hasattr(e, "errno"): -            errno = e.errno -        else: -            errno = e.args[0] - -        if errno == 98: -            self.core.log.warning(_("Click'N'Load: Port 9666 already in use")) -            return -        thread.start_new_thread(server, (self,) + settings) -    except: -        thread.start_new_thread(server, (self,) + settings) - - -def forward(source, destination): -    string = ' ' -    while string: -        string = source.recv(1024) -        if string: -            destination.sendall(string) -        else: -            #source.shutdown(socket.SHUT_RD) -            destination.shutdown(socket.SHUT_WR) diff --git a/module/plugins/hooks/DeathByCaptcha.py b/module/plugins/hooks/DeathByCaptcha.py deleted file mode 100644 index 59ff40ded..000000000 --- a/module/plugins/hooks/DeathByCaptcha.py +++ /dev/null @@ -1,210 +0,0 @@ -# -*- coding: utf-8 -*- -""" -    This program is free software; you can redistribute it and/or modify -    it under the terms of the GNU General Public License as published by -    the Free Software Foundation; either version 3 of the License, -    or (at your option) any later version. - -    This program is distributed in the hope that it will be useful, -    but WITHOUT ANY WARRANTY; without even the implied warranty of -    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. -    See the GNU General Public License for more details. - -    You should have received a copy of the GNU General Public License -    along with this program; if not, see <http://www.gnu.org/licenses/>. - -    @author: mkaay, RaNaN, zoidberg -""" -from __future__ import with_statement - -from thread import start_new_thread -from pycurl import FORM_FILE, HTTPHEADER, RESPONSE_CODE -from time import sleep -from base64 import b64encode -import re - -from module.network.RequestFactory import getURL, getRequest -from module.network.HTTPRequest import BadHeader -from module.plugins.Hook import Hook -from module.common.json_layer import json_loads - -class DeathByCaptchaException(Exception): -    DBC_ERRORS = {'not-logged-in': 'Access denied, check your credentials', -                  'invalid-credentials': 'Access denied, check your credentials', -                  'banned': 'Access denied, account is suspended', -                  'insufficient-funds': 'Insufficient account balance to decrypt CAPTCHA', -                  'invalid-captcha': 'CAPTCHA is not a valid image', -                  'service-overload': 'CAPTCHA was rejected due to service overload, try again later', -                  'invalid-request': 'Invalid request', -                  'timed-out': 'No CAPTCHA solution received in time' }  -     -    def __init__(self, err): -        self.err = err - -    def getCode(self): -        return self.err -         -    def getDesc(self): -        if self.err in self.DBC_ERRORS.keys(): -            return self.DBC_ERRORS[self.err] -        else: -            return self.err - -    def __str__(self): -        return "<DeathByCaptchaException %s>" % self.err - -    def __repr__(self): -        return "<DeathByCaptchaException %s>" % self.err - -class DeathByCaptcha(Hook): -    __name__ = "DeathByCaptcha" -    __version__ = "0.03" -    __description__ = """send captchas to DeathByCaptcha.com""" -    __config__ = [("activated", "bool", "Activated", False), -                  ("username", "str", "Username", ""), -                  ("passkey", "password", "Password", ""), -                  ("force", "bool", "Force DBC even if client is connected", False)] -    __author_name__ = ("RaNaN", "zoidberg") -    __author_mail__ = ("RaNaN@pyload.org", "zoidberg@mujmail.cz") - -    API_URL = "http://api.dbcapi.me/api/" - -    def setup(self): -        self.info = {} - -    def call_api(self, api="captcha", post=False, multipart=False): -        req = getRequest() -        req.c.setopt(HTTPHEADER, ["Accept: application/json",  -                                  "User-Agent: pyLoad %s" % self.core.version]) -         -        if post: -            if not isinstance(post, dict): -                post = {} -            post.update({"username": self.getConfig("username"), -                         "password": self.getConfig("passkey")})                           -         -        response = None -        try: -            json = req.load("%s%s" % (self.API_URL, api),  -                            post = post, -                            multipart=multipart) -            self.logDebug(json)             -            response = json_loads(json) -             -            if "error" in response: -                raise DeathByCaptchaException(response['error']) -            elif "status" not in response: -                raise DeathByCaptchaException(str(response)) -             -        except BadHeader, e: -            if 403 == e.code: -                raise DeathByCaptchaException('not-logged-in')             -            elif 413 == e.code: -                raise DeathByCaptchaException('invalid-captcha') -            elif 503 == e.code: -                raise DeathByCaptchaException('service-overload') -            elif e.code in (400, 405): -                raise DeathByCaptchaException('invalid-request') -            else: -                raise -                                                    -        finally: -            req.close() -             -        return response -         -    def getCredits(self): -        response = self.call_api("user", True) - -        if 'is_banned' in response and response['is_banned']: -            raise DeathByCaptchaException('banned') -        elif 'balance' in response and 'rate' in response: -            self.info.update(response) -        else: -            raise DeathByCaptchaException(response) -             -    def getStatus(self): -        response = self.call_api("status", False) - -        if 'is_service_overloaded' in response and response['is_service_overloaded']: -            raise DeathByCaptchaException('service-overload') - -    def submit(self, captcha, captchaType="file", match=None): -        #workaround multipart-post bug in HTTPRequest.py  -        if re.match("^[A-Za-z0-9]*$", self.getConfig("passkey")): -            multipart = True -            data = (FORM_FILE, captcha) -        else: -            multipart = False -            with open(captcha, 'rb') as f: -                data = f.read() -            data = "base64:" + b64encode(data)          -         -        response = self.call_api("captcha", {"captchafile": data}, multipart) -         -        if "captcha" not in response: -            raise DeathByCaptchaException(response) -        ticket = response['captcha'] -         -        for i in range(24): -            sleep(5) -            response = self.call_api("captcha/%d" % ticket, False)                -            if response['text'] and response['is_correct']: -                break -        else: -            raise DeathByCaptchaException('timed-out')             -                 -        result = response['text'] -        self.logDebug("result %s : %s" % (ticket,result)) - -        return ticket, result - -    def newCaptchaTask(self, task): -        if "service" in task.data: -            return False -     -        if not task.isTextual(): -            return False - -        if not self.getConfig("username") or not self.getConfig("passkey"): -            return False - -        if self.core.isClientConnected() and not self.getConfig("force"): -            return False -         -        try: -            self.getStatus() -            self.getCredits()                                                          -        except DeathByCaptchaException, e: -            self.logError(e.getDesc()) -            return False -         -        balance, rate = self.info["balance"], self.info["rate"] -        self.logInfo("Account balance: US$%.3f (%d captchas left at %.2f cents each)" % (balance / 100, balance // rate, rate)) -             -        if balance > rate:             -            task.handler.append(self) -            task.data['service'] = self.__name__ -            task.setWaiting(180) -            start_new_thread(self.processCaptcha, (task,))         - -    def captchaInvalid(self, task): -        if task.data['service'] == self.__name__ and "ticket" in task.data: -            try: -                response = self.call_api("captcha/%d/report" % task.data["ticket"], True) -            except DeathByCaptchaException, e: -                self.logError(e.getDesc()) -            except Exception, e: -                self.logError(e) - -    def processCaptcha(self, task): -        c = task.captchaFile -        try: -            ticket, result = self.submit(c) -        except DeathByCaptchaException, e: -            task.error = e.getCode() -            self.logError(e.getDesc()) -            return - -        task.data["ticket"] = ticket -        task.setResult(result)
\ No newline at end of file diff --git a/module/plugins/hooks/DownloadScheduler.py b/module/plugins/hooks/DownloadScheduler.py deleted file mode 100644 index 7cadede38..000000000 --- a/module/plugins/hooks/DownloadScheduler.py +++ /dev/null @@ -1,78 +0,0 @@ -# -*- coding: utf-8 -*- - -""" -    This program is free software; you can redistribute it and/or modify -    it under the terms of the GNU General Public License as published by -    the Free Software Foundation; either version 3 of the License, -    or (at your option) any later version. - -    This program is distributed in the hope that it will be useful, -    but WITHOUT ANY WARRANTY; without even the implied warranty of -    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. -    You should have received a copy of the GNU General Public License -    along with this program; if not, see <http://www.gnu.org/licenses/>. -     -    @author: zoidberg -    Original idea by new.cze -""" - -import re -from time import localtime -from module.plugins.Hook import Hook - -class DownloadScheduler(Hook): -    __name__ = "DownloadScheduler" -    __version__ = "0.20" -    __description__ = """Download Scheduler""" -    __config__ = [("activated", "bool", "Activated", "False"),                   -                  ("timetable", "str", "List time periods as hh:mm full or number(kB/s)", "0:00 full, 7:00 250, 10:00 0, 17:00 150")] -    __author_name__ = ("zoidberg") -    __author_mail__ = ("zoidberg@mujmail.cz") -     -    def setup(self): -        self.cb = None # callback to scheduler job; will be by removed hookmanager when hook unloaded        -     -    def coreReady(self): -        self.updateSchedule() -         -    def updateSchedule(self, schedule = None):         -        if schedule is None:  -            schedule = self.getConfig("timetable")                    -         -        schedule = re.findall("(\d{1,2}):(\d{2})[\s]*(-?\d+)", schedule.lower().replace("full", "-1").replace("none", "0"))          -        if not schedule: -            self.logError("Invalid schedule") -            return -         -        t0 = localtime() -        now = (t0.tm_hour, t0.tm_min, t0.tm_sec, "X") -        schedule = sorted([(int(x[0]), int(x[1]), 0, int(x[2])) for x in schedule] + [now]) -     -        self.logDebug("Schedule", schedule)       -       -        for i, v in enumerate(schedule): -            if v[3] == "X": -                last, next = schedule[i-1], schedule[(i+1) % len(schedule)] -                self.logDebug("Now/Last/Next", now, last, next) -                  -                self.setDownloadSpeed(last[3])  -                 -                next_time = (((24 + next[0] - now[0])* 60 + next[1] - now[1]) * 60 + next[2] - now[2]) % 86400 -                self.core.scheduler.removeJob(self.cb) -                self.cb = self.core.scheduler.addJob(next_time, self.updateSchedule, threaded=False)                                      -                 -    def setDownloadSpeed(self, speed):      -        if speed == 0: -            self.logInfo("Stopping download server. (Running downloads will not be aborted.)") -            self.core.api.pauseServer() -        else: -            self.core.api.unpauseServer() -             -            if speed > 0: -                self.logInfo("Setting download speed to %d kB/s" % speed) -                self.core.api.setConfigValue("download","limit_speed",1) -                self.core.api.setConfigValue("download","max_speed",speed) -            else: -                self.logInfo("Setting download speed to FULL") -                self.core.api.setConfigValue("download","limit_speed",0) -                self.core.api.setConfigValue("download","max_speed",-1)
\ No newline at end of file diff --git a/module/plugins/hooks/EasybytezCom.py b/module/plugins/hooks/EasybytezCom.py deleted file mode 100644 index 21a988555..000000000 --- a/module/plugins/hooks/EasybytezCom.py +++ /dev/null @@ -1,36 +0,0 @@ -# -*- coding: utf-8 -*- - -from module.network.RequestFactory import getURL -from module.plugins.internal.MultiHoster import MultiHoster -import re - -def getConfigSet(option): -    s = set(option.lower().replace(',','|').split('|')) -    s.discard(u'') -    return s - -class EasybytezCom(MultiHoster): -    __name__ = "EasybytezCom" -    __version__ = "0.02" -    __type__ = "hook" -    __config__ = [("activated", "bool", "Activated", "False"), -                  ("hosterListMode", "all;listed;unlisted", "Use for hosters (if supported)", "all"), -                  ("hosterList", "str", "Hoster list (comma separated)", "")] -    __description__ = """EasyBytez.com hook plugin""" -    __author_name__ = ("zoidberg") -    __author_mail__ = ("zoidberg@mujmail.cz") - -    def getHoster(self): - -        hoster = set(['2shared.com', 'easy-share.com', 'filefactory.com', 'fileserve.com', 'filesonic.com', 'hotfile.com', 'mediafire.com', 'megaupload.com', 'netload.in', 'rapidshare.com', 'uploading.com', 'wupload.com', 'oron.com', 'uploadstation.com', 'ul.to', 'uploaded.to'])    -         -        configMode = self.getConfig('hosterListMode') -        if configMode in ("listed", "unlisted"): -            configList = set(self.getConfig('hosterList').strip().lower().replace('|',',').replace(';',',').split(',')) -            configList.discard(u'') -            if configMode == "listed": -                hoster &= configList -            else: -                hoster -= configList -         -        return list(hoster)
\ No newline at end of file diff --git a/module/plugins/hooks/Ev0InFetcher.py b/module/plugins/hooks/Ev0InFetcher.py deleted file mode 100644 index 5941cf38c..000000000 --- a/module/plugins/hooks/Ev0InFetcher.py +++ /dev/null @@ -1,87 +0,0 @@ -# -*- coding: utf-8 -*- -""" -    This program is free software; you can redistribute it and/or modify -    it under the terms of the GNU General Public License as published by -    the Free Software Foundation; either version 3 of the License, -    or (at your option) any later version. - -    This program is distributed in the hope that it will be useful, -    but WITHOUT ANY WARRANTY; without even the implied warranty of -    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. -    See the GNU General Public License for more details. - -    You should have received a copy of the GNU General Public License -    along with this program; if not, see <http://www.gnu.org/licenses/>. - -    @author: mkaay -""" -from module.lib import feedparser -from time import mktime, time - -from module.plugins.Hook import Hook - -class Ev0InFetcher(Hook): -    __name__ = "Ev0InFetcher" -    __version__ = "0.2" -    __description__ = """checks rss feeds for ev0.in""" -    __config__ = [("activated", "bool", "Activated", "False"), -                  ("interval", "int", "Check interval in minutes", "10"), -                  ("queue", "bool", "Move new shows directly to Queue", False), -                  ("shows", "str", "Shows to check for (comma seperated)", ""), -                  ("quality", "xvid;x264;rmvb", "Video Format", "xvid"), -                  ("hoster", "str", "Hoster to use (comma seperated)", "NetloadIn,RapidshareCom,MegauploadCom,HotfileCom")] -    __author_name__ = ("mkaay") -    __author_mail__ = ("mkaay@mkaay.de") - -    def setup(self): -        self.interval = self.getConfig("interval") * 60 - -    def filterLinks(self, links): -        results = self.core.pluginManager.parseUrls(links) -        sortedLinks = {} -         -        for url, hoster in results: -            if hoster not in sortedLinks: -                sortedLinks[hoster] = [] -            sortedLinks[hoster].append(url) -         -        for h in self.getConfig("hoster").split(","): -            try: -                return sortedLinks[h.strip()] -            except: -                continue -        return [] -     -    def periodical(self): -        def normalizefiletitle(filename): -            filename = filename.replace('.', ' ') -            filename = filename.replace('_', ' ') -            filename = filename.lower() -            return filename -         -        shows = [s.strip() for s in self.getConfig("shows").split(",")] -         -        feed = feedparser.parse("http://feeds.feedburner.com/ev0in/%s?format=xml" % self.getConfig("quality")) - -        showStorage = {} -        for show in shows: -            showStorage[show] = int(self.getStorage("show_%s_lastfound" % show, 0)) -         -        found = False -        for item in feed['items']: -            for show, lastfound in showStorage.iteritems(): -                if show.lower() in normalizefiletitle(item['title']) and lastfound < int(mktime(item.date_parsed)): -                    links = self.filterLinks(item['description'].split("<br />")) -                    packagename = item['title'].encode("utf-8") -                    self.core.log.info("Ev0InFetcher: new episode '%s' (matched '%s')" % (packagename, show)) -                    self.core.api.addPackage(packagename, links, 1 if self.getConfig("queue") else 0) -                    self.setStorage("show_%s_lastfound" % show, int(mktime(item.date_parsed))) -                    found = True -        if not found: -            #self.core.log.debug("Ev0InFetcher: no new episodes found") -            pass - -        for show, lastfound in self.getStorage().iteritems(): -            if int(lastfound) > 0 and int(lastfound) + (3600*24*30) < int(time()): -                self.delStorage("show_%s_lastfound" % show) -                self.core.log.debug("Ev0InFetcher: cleaned '%s' record" % show) diff --git a/module/plugins/hooks/ExpertDecoders.py b/module/plugins/hooks/ExpertDecoders.py deleted file mode 100644 index 2e66e49ca..000000000 --- a/module/plugins/hooks/ExpertDecoders.py +++ /dev/null @@ -1,112 +0,0 @@ -# -*- coding: utf-8 -*- -""" -    This program is free software; you can redistribute it and/or modify -    it under the terms of the GNU General Public License as published by -    the Free Software Foundation; either version 3 of the License, -    or (at your option) any later version. - -    This program is distributed in the hope that it will be useful, -    but WITHOUT ANY WARRANTY; without even the implied warranty of -    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. -    See the GNU General Public License for more details. - -    You should have received a copy of the GNU General Public License -    along with this program; if not, see <http://www.gnu.org/licenses/>. - -    @author: mkaay, RaNaN, zoidberg -""" -from __future__ import with_statement - -from thread import start_new_thread -from pycurl import FORM_FILE, LOW_SPEED_TIME -from uuid import uuid4 -from base64 import b64encode - -from module.network.RequestFactory import getURL, getRequest -from module.network.HTTPRequest import BadHeader - -from module.plugins.Hook import Hook - -class ExpertDecoders(Hook): -    __name__ = "ExpertDecoders" -    __version__ = "0.01" -    __description__ = """send captchas to expertdecoders.com""" -    __config__ = [("activated", "bool", "Activated", False), -                  ("force", "bool", "Force CT even if client is connected", False), -                  ("passkey", "password", "Access key", ""),] -    __author_name__ = ("RaNaN", "zoidberg") -    __author_mail__ = ("RaNaN@pyload.org", "zoidberg@mujmail.cz") - -    API_URL = "http://www.fasttypers.org/imagepost.ashx" - -    def setup(self): -        self.info = {} - -    def getCredits(self):     -        response = getURL(self.API_URL, post = { "key": self.getConfig("passkey"), "action": "balance" }) -         -        if response.isdigit():                 -            self.logInfo(_("%s credits left") % response) -            self.info["credits"] = credits = int(response) -            return credits  -        else: -            self.logError(response) -            return 0 -         -    def processCaptcha(self, task):         -        task.data["ticket"] = ticket = uuid4() -        result = None -         -        with open(task.captchaFile, 'rb') as f: -            data = f.read()         -        data = b64encode(data)          -        #self.logDebug("%s: %s : %s" % (ticket, task.captchaFile, data)) - -        req = getRequest() -        #raise timeout threshold -        req.c.setopt(LOW_SPEED_TIME, 80) -         -        try: -            result = req.load(self.API_URL,  -                              post={ "action": "upload", -                                     "key": self.getConfig("passkey"), -                                     "file": data,  -                            		   	 "gen_task_id": ticket } -                              ) -        finally: -            req.close() - -        self.logDebug("result %s : %s" % (ticket, result)) -        task.setResult(result) - -    def newCaptchaTask(self, task): -        if not task.isTextual(): -            return False - -        if not self.getConfig("passkey"): -            return False - -        if self.core.isClientConnected() and not self.getConfig("force"): -            return False - -        if self.getCredits() > 0: -            task.handler.append(self) -            task.setWaiting(100) -            start_new_thread(self.processCaptcha, (task,)) - -        else: -            self.logInfo(_("Your ExpertDecoders Account has not enough credits")) - -    def captchaInvalid(self, task): -        if "ticket" in task.data: -             -            try: -                response = getURL(self.API_URL,  -                              post={ "action": "refund", -                                     "key": self.getConfig("passkey"), -                                     "gen_task_id": task.data["ticket"] } -                              ) -                self.logInfo("Request refund: %s" % response) - -            except BadHeader, e: -                self.logError("Could not send refund request.", str(e))
\ No newline at end of file diff --git a/module/plugins/hooks/ExternalScripts.py b/module/plugins/hooks/ExternalScripts.py deleted file mode 100644 index 2e77f1dae..000000000 --- a/module/plugins/hooks/ExternalScripts.py +++ /dev/null @@ -1,119 +0,0 @@ -# -*- coding: utf-8 -*- - -""" -    This program is free software; you can redistribute it and/or modify -    it under the terms of the GNU General Public License as published by -    the Free Software Foundation; either version 3 of the License, -    or (at your option) any later version. - -    This program is distributed in the hope that it will be useful, -    but WITHOUT ANY WARRANTY; without even the implied warranty of -    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. -    See the GNU General Public License for more details. - -    You should have received a copy of the GNU General Public License -    along with this program; if not, see <http://www.gnu.org/licenses/>. - -    @author: mkaay -    @interface-version: 0.1 -""" - -import subprocess -from os import listdir, access, X_OK, makedirs -from os.path import join, exists, basename - -from module.plugins.Hook import Hook -from module.utils import save_join - -class ExternalScripts(Hook): -    __name__ = "ExternalScripts" -    __version__ = "0.21" -    __description__ = """Run external scripts""" -    __config__ = [("activated", "bool", "Activated", "True")] -    __author_name__ = ("mkaay", "RaNaN", "spoob") -    __author_mail__ = ("mkaay@mkaay.de", "ranan@pyload.org", "spoob@pyload.org") - -    event_list = ["unrarFinished", "allDownloadsFinished", "allDownloadsProcessed"] - -    def setup(self): -        self.scripts = {} - -        folders = ['download_preparing', 'download_finished', 'package_finished', -                   'before_reconnect', 'after_reconnect', 'unrar_finished', -                   'all_dls_finished', 'all_dls_processed'] - -        for folder in folders: - -            self.scripts[folder] = [] - -            self.initPluginType(folder, join(pypath, 'scripts', folder)) -            self.initPluginType(folder, join('scripts', folder)) - -        for script_type, names in self.scripts.iteritems(): -            if names: -                self.logInfo((_("Installed scripts for %s: ") % script_type ) + ", ".join([basename(x) for x in names])) - - -    def initPluginType(self, folder, path): -        if not exists(path): -            try: -                makedirs(path) -            except : -                self.logDebug("Script folder %s not created" % folder) -                return - -        for f in listdir(path): -            if f.startswith("#") or f.startswith(".") or f.startswith("_") or f.endswith("~") or f.endswith(".swp"): -                continue - -            if not access(join(path,f), X_OK): -                self.logWarning(_("Script not executable:") + " %s/%s" % (folder, f)) - -            self.scripts[folder].append(join(path, f)) - -    def callScript(self, script, *args): -        try: -            cmd = [script] + [str(x) if not isinstance(x, basestring) else x for x in args] -            #output goes to pyload -            subprocess.Popen(cmd, bufsize=-1) -        except Exception, e: -            self.logError(_("Error in %(script)s: %(error)s") % { "script" :basename(script), "error": str(e)}) - -    def downloadPreparing(self, pyfile): -        for script in self.scripts['download_preparing']: -            self.callScript(script, pyfile.pluginname, pyfile.url, pyfile.id) - -    def downloadFinished(self, pyfile): -        for script in self.scripts['download_finished']: -            self.callScript(script, pyfile.pluginname, pyfile.url, pyfile.name, pyfile.id, -                            save_join(self.core.config['general']['download_folder'], pyfile.package().folder, pyfile.name), -                            pyfile.id) - - -    def packageFinished(self, pypack): -        for script in self.scripts['package_finished']: -            folder = self.core.config['general']['download_folder'] -            folder = save_join(folder, pypack.folder) - -            self.callScript(script, pypack.name, folder, pypack.id) - -    def beforeReconnecting(self, ip): -        for script in self.scripts['before_reconnect']: -            self.callScript(script, ip) - -    def afterReconnecting(self, ip): -        for script in self.scripts['after_reconnect']: -            self.callScript(script, ip) - -    def unrarFinished(self, folder, fname): -        for script in self.scripts["unrar_finished"]: -            self.callScript(script, folder, fname) - -    def allDownloadsFinished(self): -        for script in self.scripts["all_dls_finished"]: -            self.callScript(script) - -    def allDownloadsProcessed(self): -        for script in self.scripts["all_dls_processed"]: -            self.callScript(script) - diff --git a/module/plugins/hooks/ExtractArchive.py b/module/plugins/hooks/ExtractArchive.py deleted file mode 100644 index c789495ca..000000000 --- a/module/plugins/hooks/ExtractArchive.py +++ /dev/null @@ -1,315 +0,0 @@ -#!/usr/bin/env python -# -*- coding: utf-8 -*- - -import sys -import os -from os import remove, chmod, makedirs -from os.path import exists, basename, isfile, isdir, join -from traceback import print_exc -from copy import copy - -# monkey patch bug in python 2.6 and lower -# see http://bugs.python.org/issue6122 -# http://bugs.python.org/issue1236 -# http://bugs.python.org/issue1731717 -if sys.version_info < (2, 7) and os.name != "nt": -    from subprocess import Popen -    import errno - -    def _eintr_retry_call(func, *args): -        while True: -            try: -                return func(*args) -            except OSError, e: -                if e.errno == errno.EINTR: -                    continue -                raise - -    # unsued timeout option for older python version -    def wait(self, timeout=0): -        """Wait for child process to terminate.  Returns returncode -        attribute.""" -        if self.returncode is None: -            try: -                pid, sts = _eintr_retry_call(os.waitpid, self.pid, 0) -            except OSError, e: -                if e.errno != errno.ECHILD: -                    raise -                    # This happens if SIGCLD is set to be ignored or waiting -                # for child processes has otherwise been disabled for our -                # process.  This child is dead, we can't get the status. -                sts = 0 -            self._handle_exitstatus(sts) -        return self.returncode - -    Popen.wait = wait - -if os.name != "nt": -    from os import chown -    from pwd import getpwnam -    from grp import getgrnam - -from module.utils import save_join, fs_encode -from module.plugins.Hook import Hook, threaded, Expose -from module.plugins.internal.AbstractExtractor import ArchiveError, CRCError, WrongPassword - -class ExtractArchive(Hook): -    """ -    Provides: unrarFinished (folder, filename) -    """ -    __name__ = "ExtractArchive" -    __version__ = "0.12" -    __description__ = "Extract different kind of archives" -    __config__ = [("activated", "bool", "Activated", True), -        ("fullpath", "bool", "Extract full path", True), -        ("overwrite", "bool", "Overwrite files", True), -        ("passwordfile", "file", "password file", "unrar_passwords.txt"), -        ("deletearchive", "bool", "Delete archives when done", False), -        ("subfolder", "bool", "Create subfolder for each package", False), -        ("destination", "folder", "Extract files to", ""), -        ("recursive", "bool", "Extract archives in archvies", True), -        ("queue", "bool", "Wait for all downloads to be finished", True), -        ("renice", "int", "CPU Priority", 0), ] -    __author_name__ = ("pyload Team") -    __author_mail__ = ("admin<at>pyload.org") - -    event_list = ["allDownloadsProcessed"] - -    def setup(self): -        self.plugins = [] -        self.passwords = [] -        names = [] - -        for p in ("UnRar", "UnZip"): -            try: -                module = self.core.pluginManager.loadModule("internal", p) -                klass = getattr(module, p) -                if klass.checkDeps(): -                    names.append(p) -                    self.plugins.append(klass) - -            except OSError, e: -                if e.errno == 2: -                    self.logInfo(_("No %s installed") % p) -                else: -                    self.logWarning(_("Could not activate %s") % p, str(e)) -                    if self.core.debug: -                        print_exc() - -            except Exception, e: -                self.logWarning(_("Could not activate %s") % p, str(e)) -                if self.core.debug: -                    print_exc() - -        if names: -            self.logInfo(_("Activated") + " " + " ".join(names)) -        else: -            self.logInfo(_("No Extract plugins activated")) - -        # queue with package ids -        self.queue = [] - -    @Expose -    def extractPackage(self, id): -        """ Extract package with given id""" -        self.manager.startThread(self.extract, [id]) - -    def packageFinished(self, pypack): -        if self.getConfig("queue"): -            self.logInfo(_("Package %s queued for later extracting") % pypack.name) -            self.queue.append(pypack.id) -        else: -            self.manager.startThread(self.extract, [pypack.id]) - - -    @threaded -    def allDownloadsProcessed(self, thread): -        local = copy(self.queue) -        del self.queue[:] -        self.extract(local, thread) - - -    def extract(self, ids, thread=None): -        # reload from txt file -        self.reloadPasswords() - -        # dl folder -        dl = self.config['general']['download_folder'] - -        extracted = [] - -        #iterate packages -> plugins -> targets -        for pid in ids: -            p = self.core.files.getPackage(pid) -            self.logInfo(_("Check package %s") % p.name) -            if not p: continue - -            # determine output folder -            out = save_join(dl, p.folder, "") -            # force trailing slash - -            if self.getConfig("destination") and self.getConfig("destination").lower() != "none": - -                out = save_join(dl, p.folder, self.getConfig("destination"), "") -                #relative to package folder if destination is relative, otherwise absolute path overwrites them - -                if self.getConf("subfolder"): -                    out = join(out, fs_encode(p.folder)) - -                if not exists(out): -                    makedirs(out) - -            files_ids = [(save_join(dl, p.folder, x["name"]), x["id"]) for x in p.getChildren().itervalues()] -            matched = False - -            # check as long there are unseen files -            while files_ids: -                new_files_ids = [] - -                for plugin in self.plugins: -                    targets = plugin.getTargets(files_ids) -                    if targets: -                        self.logDebug("Targets for %s: %s" % (plugin.__name__, targets)) -                        matched = True -                    for target, fid in targets: -                        if target in extracted: -                            self.logDebug(basename(target), "skipped") -                            continue -                        extracted.append(target) #prevent extracting same file twice - -                        klass = plugin(self, target, out, self.getConfig("fullpath"), self.getConfig("overwrite"), -                            self.getConfig("renice")) -                        klass.init() - -                        self.logInfo(basename(target), _("Extract to %s") % out) -                        new_files = self.startExtracting(klass, fid, p.password.strip().splitlines(), thread) -                        self.logDebug("Extracted: %s" % new_files) -                        self.setPermissions(new_files) - -                        for file in new_files: -                            if not exists(file): -                                self.logDebug("new file %s does not exists" % file) -                                continue -                            if self.getConfig("recursive") and isfile(file): -                                new_files_ids.append((file, fid)) #append as new target - -                files_ids = new_files_ids # also check extracted files - -            if not matched: self.logInfo(_("No files found to extract")) -	 - - -    def startExtracting(self, plugin, fid, passwords, thread): -        pyfile = self.core.files.getFile(fid) -        if not pyfile: return [] - -        pyfile.setCustomStatus(_("extracting")) -        thread.addActive(pyfile) #keep this file until everything is done - -        try: -            progress = lambda x: pyfile.setProgress(x) -            success = False - -            if not plugin.checkArchive(): -                plugin.extract(progress) -                success = True -            else: -                self.logInfo(basename(plugin.file), _("Password protected")) -                self.logDebug("Passwords: %s" % str(passwords)) - -                pwlist = copy(self.getPasswords()) -                #remove already supplied pws from list (only local) -                for pw in passwords: -                    if pw in pwlist: pwlist.remove(pw) - -                for pw in passwords + pwlist: -                    try: -                        self.logDebug("Try password: %s" % pw) -                        if plugin.checkPassword(pw): -                            plugin.extract(progress, pw) -                            self.addPassword(pw) -                            success = True -                            break -                    except WrongPassword: -                        self.logDebug("Password was wrong") - -            if not success: -                self.logError(basename(plugin.file), _("Wrong password")) -                return [] - -            if self.core.debug: -                self.logDebug("Would delete: %s" % ", ".join(plugin.getDeleteFiles())) - -            if self.getConfig("deletearchive"): -                files = plugin.getDeleteFiles() -                self.logInfo(_("Deleting %s files") % len(files)) -                for f in files: -                    if exists(f): remove(f) -                    else: self.logDebug("%s does not exists" % f) - -            self.logInfo(basename(plugin.file), _("Extracting finished")) -            self.manager.dispatchEvent("unrarFinished", plugin.out, plugin.file) - -            return plugin.getExtractedFiles() - - -        except ArchiveError, e: -            self.logError(basename(plugin.file), _("Archive Error"), str(e)) -        except CRCError: -            self.logError(basename(plugin.file), _("CRC Mismatch")) -        except Exception, e: -            if self.core.debug: -                print_exc() -            self.logError(basename(plugin.file), _("Unknown Error"), str(e)) - -        return [] - -    @Expose -    def getPasswords(self): -        """ List of saved passwords """ -        return self.passwords - - -    def reloadPasswords(self): -        pwfile = self.getConfig("passwordfile") -        if not exists(pwfile): -            open(pwfile, "wb").close() - -        passwords = [] -        f = open(pwfile, "rb") -        for pw in f.read().splitlines(): -            passwords.append(pw) -        f.close() - -        self.passwords = passwords - - -    @Expose -    def addPassword(self, pw): -        """  Adds a password to saved list""" -        pwfile = self.getConfig("passwordfile") - -        if pw in self.passwords: self.passwords.remove(pw) -        self.passwords.insert(0, pw) - -        f = open(pwfile, "wb") -        for pw in self.passwords: -            f.write(pw + "\n") -        f.close() - -    def setPermissions(self, files): -        for f in files: -            if not exists(f): continue -            try: -                if self.core.config["permission"]["change_file"]: -                    if isfile(f): -                        chmod(f, int(self.core.config["permission"]["file"], 8)) -                    elif isdir(f): -                        chmod(f, int(self.core.config["permission"]["folder"], 8)) - -                if self.core.config["permission"]["change_dl"] and os.name != "nt": -                    uid = getpwnam(self.config["permission"]["user"])[2] -                    gid = getgrnam(self.config["permission"]["group"])[2] -                    chown(f, uid, gid) -            except Exception, e: -                self.log.warning(_("Setting User and Group failed"), e) diff --git a/module/plugins/hooks/HotFolder.py b/module/plugins/hooks/HotFolder.py deleted file mode 100644 index ee1031ad5..000000000 --- a/module/plugins/hooks/HotFolder.py +++ /dev/null @@ -1,85 +0,0 @@ -# -*- coding: utf-8 -*- - -""" -    This program is free software; you can redistribute it and/or modify -    it under the terms of the GNU General Public License as published by -    the Free Software Foundation; either version 3 of the License, -    or (at your option) any later version. - -    This program is distributed in the hope that it will be useful, -    but WITHOUT ANY WARRANTY; without even the implied warranty of -    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. -    See the GNU General Public License for more details. - -    You should have received a copy of the GNU General Public License -    along with this program; if not, see <http://www.gnu.org/licenses/>. -     -    @author: RaNaN -    @interface-version: 0.2 -""" - -from os import makedirs -from os import listdir -from os.path import exists -from os.path import join -from os.path import isfile -from shutil import move -import time - -from module.plugins.Hook import Hook - -class HotFolder(Hook): -    __name__ = "HotFolder" -    __version__ = "0.1" -    __description__ = """observe folder and file for changes and add container and links""" -    __config__ = [ ("activated", "bool", "Activated" , "False"), -                   ("folder", "str", "Folder to observe", "container"), -                   ("watch_file", "bool", "Observe link file", "False"), -                   ("keep", "bool", "Keep added containers", "True"), -                   ("file", "str", "Link file", "links.txt")] -    __threaded__ = [] -    __author_name__ = ("RaNaN") -    __author_mail__ = ("RaNaN@pyload.de") -     -    def setup(self): -        self.interval = 10 -         -    def periodical(self): -         -        if not exists(join(self.getConfig("folder"), "finished")): -            makedirs(join(self.getConfig("folder"), "finished")) -           -        if self.getConfig("watch_file"): - -            if not exists(self.getConfig("file")): -                f = open(self.getConfig("file"), "wb") -                f.close() -             -             -            f = open(self.getConfig("file"), "rb") -            content = f.read().strip() -            f.close() -            f = open(self.getConfig("file"), "wb") -            f.close() -            if content: -                name = "%s_%s.txt" % (self.getConfig("file"), time.strftime("%H-%M-%S_%d%b%Y") ) - -                f = open(join(self.getConfig("folder"), "finished", name), "wb") -                f.write(content) -                f.close() - -                self.core.api.addPackage(f.name, [f.name], 1) -               -        for f in listdir(self.getConfig("folder")): -            path = join(self.getConfig("folder"), f) -             -            if not isfile(path) or f.endswith("~") or f.startswith("#") or f.startswith("."): -                continue -             -            newpath = join(self.getConfig("folder"), "finished", f if self.getConfig("keep") else "tmp_"+f) -            move(path, newpath) -             -            self.log.info(_("Added %s from HotFolder") % f) -            self.core.api.addPackage(f, [newpath], 1) -             -        
\ No newline at end of file diff --git a/module/plugins/hooks/IRCInterface.py b/module/plugins/hooks/IRCInterface.py deleted file mode 100644 index e2737dc3a..000000000 --- a/module/plugins/hooks/IRCInterface.py +++ /dev/null @@ -1,425 +0,0 @@ -# -*- coding: utf-8 -*- - -""" -    This program is free software; you can redistribute it and/or modify -    it under the terms of the GNU General Public License as published by -    the Free Software Foundation; either version 3 of the License, -    or (at your option) any later version. - -    This program is distributed in the hope that it will be useful, -    but WITHOUT ANY WARRANTY; without even the implied warranty of -    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. -    See the GNU General Public License for more details. - -    You should have received a copy of the GNU General Public License -    along with this program; if not, see <http://www.gnu.org/licenses/>. -     -    @author: RaNaN -    @author: jeix -    @interface-version: 0.2 -""" - -from select import select -import socket -from threading import Thread -import time -from time import sleep -from traceback import print_exc -import re - -from module.plugins.Hook import Hook -from module.network.RequestFactory import getURL -from module.utils import formatSize - -from pycurl import FORM_FILE - -class IRCInterface(Thread, Hook): -    __name__ = "IRCInterface" -    __version__ = "0.1" -    __description__ = """connect to irc and let owner perform different tasks""" -    __config__ = [("activated", "bool", "Activated", "False"), -        ("host", "str", "IRC-Server Address", "Enter your server here!"), -        ("port", "int", "IRC-Server Port", "6667"), -        ("ident", "str", "Clients ident", "pyload-irc"), -        ("realname", "str", "Realname", "pyload-irc"), -        ("nick", "str", "Nickname the Client will take", "pyLoad-IRC"), -        ("owner", "str", "Nickname the Client will accept commands from", "Enter your nick here!"), -        ("info_file", "bool", "Inform about every file finished", "False"), -        ("info_pack", "bool", "Inform about every package finished", "True"), -        ("captcha", "bool", "Send captcha requests", "True")] -    __author_name__ = ("Jeix") -    __author_mail__ = ("Jeix@hasnomail.com") -     -    def __init__(self, core, manager): -        Thread.__init__(self) -        Hook.__init__(self, core, manager) -        self.setDaemon(True) -        #   self.sm = core.server_methods -        self.api = core.api #todo, only use api -         -    def coreReady(self): -        self.new_package = {} -         -        self.abort = False -         -        self.links_added = 0 -        self.more = [] - -        self.start() -         -         -    def packageFinished(self, pypack): -        try: -            if self.getConfig("info_pack"): -                self.response(_("Package finished: %s") % pypack.name) -        except: -            pass -         -    def downloadFinished(self, pyfile): -        try: -            if self.getConfig("info_file"): -                self.response(_("Download finished: %(name)s @ %(plugin)s ") % { "name" : pyfile.name, "plugin": pyfile.pluginname} ) -        except: -            pass - -    def newCaptchaTask(self, task): -        if self.getConfig("captcha") and task.isTextual(): -            task.handler.append(self) -            task.setWaiting(60) - -            page = getURL("http://www.freeimagehosting.net/upload.php", post={"attached" : (FORM_FILE, task.captchaFile)}, multipart=True) - -            url = re.search(r"\[img\]([^\[]+)\[/img\]\[/url\]", page).group(1) -            self.response(_("New Captcha Request: %s") % url) -            self.response(_("Answer with 'c %s text on the captcha'") % task.id) - -    def run(self): -        # connect to IRC etc. -        self.sock = socket.socket() -        host = self.getConfig("host") -        self.sock.connect((host, self.getConfig("port"))) -        nick = self.getConfig("nick") -        self.sock.send("NICK %s\r\n" % nick) -        self.sock.send("USER %s %s bla :%s\r\n" % (nick, host, nick)) -        for t in self.getConfig("owner").split(): -            if t.strip().startswith("#"): -                self.sock.send("JOIN %s\r\n" % t.strip()) -        self.log.info("pyLoad IRC: Connected to %s!" % host) -        self.log.info("pyLoad IRC: Switching to listening mode!") -        try:         -            self.main_loop() -             -        except IRCError, ex: -            self.sock.send("QUIT :byebye\r\n") -            print_exc() -            self.sock.close() - -             -    def main_loop(self): -        readbuffer = "" -        while True: -            sleep(1) -            fdset = select([self.sock], [], [], 0) -            if self.sock not in fdset[0]: -                continue -             -            if self.abort: -                raise IRCError("quit") -             -            readbuffer += self.sock.recv(1024) -            temp = readbuffer.split("\n") -            readbuffer = temp.pop() - -            for line in temp: -                line  = line.rstrip() -                first = line.split() - -                if first[0] == "PING": -                    self.sock.send("PONG %s\r\n" % first[1]) -                     -                if first[0] == "ERROR": -                    raise IRCError(line) -                     -                msg = line.split(None, 3) -                if len(msg) < 4: -                    continue -                     -                msg = { -                    "origin":msg[0][1:], -                    "action":msg[1], -                    "target":msg[2], -                    "text":msg[3][1:] -                } -                 -                self.handle_events(msg) -         -         -    def handle_events(self, msg): -        if not msg["origin"].split("!", 1)[0] in self.getConfig("owner").split(): -            return -             -        if msg["target"].split("!", 1)[0] != self.getConfig("nick"): -            return -             -        if msg["action"] != "PRIVMSG": -            return -             -        # HANDLE CTCP ANTI FLOOD/BOT PROTECTION -        if msg["text"] == "\x01VERSION\x01": -            self.log.debug("Sending CTCP VERSION.") -            self.sock.send("NOTICE %s :%s\r\n" % (msg['origin'], "pyLoad! IRC Interface")) -            return -        elif msg["text"] == "\x01TIME\x01": -            self.log.debug("Sending CTCP TIME.") -            self.sock.send("NOTICE %s :%d\r\n" % (msg['origin'], time.time())) -            return -        elif msg["text"] == "\x01LAG\x01": -            self.log.debug("Received CTCP LAG.") # don't know how to answer -            return -          -        trigger = "pass" -        args = None - -        try: -            temp = msg["text"].split() -            trigger = temp[0] -            if len(temp) > 1: -                args = temp[1:] -        except: -            pass - -        handler = getattr(self, "event_%s" % trigger, self.event_pass) -        try: -            res = handler(args) -            for line in res: -                self.response(line, msg["origin"]) -        except Exception, e: -            self.log.error("pyLoad IRC: "+ repr(e)) -         -         -    def response(self, msg, origin=""): -        if origin == "": -            for t in self.getConfig("owner").split(): -                self.sock.send("PRIVMSG %s :%s\r\n" % (t.strip(), msg)) -        else: -            self.sock.send("PRIVMSG %s :%s\r\n" % (origin.split("!", 1)[0], msg)) -         -         -#### Events -    def event_pass(self, args): -        return [] -         -    def event_status(self, args): -        downloads = self.api.statusDownloads() -        if not downloads: -            return ["INFO: There are no active downloads currently."] -             -        temp_progress = "" -        lines = ["ID - Name - Status - Speed - ETA - Progress"] -        for data in downloads: - -            if data.status == 5: -                temp_progress = data.format_wait -            else: -                temp_progress = "%d%% (%s)" % (data.percent, data.format_size) - -            lines.append("#%d - %s - %s - %s - %s - %s" % -                     ( -                     data.fid, -                     data.name, -                     data.statusmsg, -                     "%s/s" % formatSize(data.speed), -                     "%s" % data.format_eta, -                     temp_progress -                     ) -                     ) -        return lines -             -    def event_queue(self, args): -        ps = self.api.getQueue() -         -        if not ps: -            return ["INFO: There are no packages in queue."] -         -        lines = [] -        for pack in ps: -            lines.append('PACKAGE #%s: "%s" with %d links.' % (pack.pid, pack.name, len(pack.fids) )) -                 -        return lines -         -    def event_collector(self, args): -        ps = self.api.getCollector() -        if not ps: -            return ["INFO: No packages in collector!"] -         -        lines = [] -        for pack in ps: -            lines.append('PACKAGE #%s: "%s" with %d links.' % (pack.pid, pack.name, len(pack.fids) )) -                 -        return lines -             -    def event_info(self, args): -        if not args: -            return ['ERROR: Use info like this: info <id>'] -             -        info = self.api.getFileData(int(args[0])) -         -        if not info: -            return ["ERROR: Link doesn't exists."] - -        return ['LINK #%s: %s (%s) [%s][%s]' % (info.fid, info.name, info.format_size, info.status_msg, -                                                info.plugin)] -         -    def event_packinfo(self, args): -        if not args: -            return ['ERROR: Use packinfo like this: packinfo <id>'] -             -        lines = [] -        pack = self.api.getPackageData(int(args[0])) -         -        if not pack: -            return ["ERROR: Package doesn't exists."] -         -        id = args[0] - -        self.more = [] -         -        lines.append('PACKAGE #%s: "%s" with %d links' % (id, pack.name, len(pack.links)) ) -        for pyfile in pack.links: -            self.more.append('LINK #%s: %s (%s) [%s][%s]' % (pyfile.fid, pyfile.name, pyfile.format_size, -                                                             pyfile.statusmsg, pyfile.plugin)) - -        if len(self.more) < 6: -            lines.extend(self.more) -            self.more = [] -        else: -            lines.extend(self.more[:6]) -            self.more = self.more[6:] -            lines.append("%d more links do display." % len(self.more)) -             -             -        return lines -     -    def event_more(self, args): -        if not self.more: -            return ["No more information to display."] -         -        lines = self.more[:6] -        self.more = self.more[6:] -        lines.append("%d more links do display." % len(self.more)) -         -        return lines -     -    def event_start(self, args): -         -        self.api.unpauseServer() -        return ["INFO: Starting downloads."] -         -    def event_stop(self, args): -     -        self.api.pauseServer() -        return ["INFO: No new downloads will be started."] -     -     -    def event_add(self, args): -        if len(args) < 2: -            return ['ERROR: Add links like this: "add <packagename|id> links". ', -                     'This will add the link <link> to to the package <package> / the package with id <id>!'] -             - -             -        pack = args[0].strip() -        links = [x.strip() for x in args[1:]] -         -        count_added = 0 -        count_failed = 0 -        try: -            id = int(pack)  -            pack = self.api.getPackageData(id) -            if not pack: -                return ["ERROR: Package doesn't exists."] -             -            #TODO add links -             -            return ["INFO: Added %d links to Package %s [#%d]" % (len(links), pack["name"], id)] -             -        except: -            # create new package -            id = self.api.addPackage(pack, links, 1) -            return ["INFO: Created new Package %s [#%d] with %d links." % (pack, id, len(links))] -              -         -    def event_del(self, args): -        if len(args) < 2: -            return ["ERROR: Use del command like this: del -p|-l <id> [...] (-p indicates that the ids are from packages, -l indicates that the ids are from links)"] -             -        if args[0] == "-p": -            ret = self.api.deletePackages(map(int, args[1:])) -            return ["INFO: Deleted %d packages!" % len(args[1:])] -             -        elif args[0] == "-l": -            ret = self.api.delLinks(map(int, args[1:])) -            return ["INFO: Deleted %d links!" % len(args[1:])] - -        else: -            return ["ERROR: Use del command like this: del <-p|-l> <id> [...] (-p indicates that the ids are from packages, -l indicates that the ids are from links)"] -             -    def event_push(self, args): -        if not args: -            return ["ERROR: Push package to queue like this: push <package id>"] - -        id = int(args[0]) -        if not self.api.getPackage_data(id): -            return ["ERROR: Package #%d does not exist." % id] - -        self.api.pushToQueue(id) -        return ["INFO: Pushed package #%d to queue." % id] - -    def event_pull(self, args): -        if not args: -            return ["ERROR: Pull package from queue like this: pull <package id>."] - -        id = int(args[0]) -        if not self.api.getPackageData(id): -            return ["ERROR: Package #%d does not exist." % id] - -        self.api.pullFromQueue(id) -        return ["INFO: Pulled package #%d from queue to collector." % id] - -    def event_c(self, args): -        """ captcha answer """ -        if not args: -            return ["ERROR: Captcha ID missing."] - -        task = self.core.captchaManager.getTaskByID(args[0]) -        if not task: -            return ["ERROR: Captcha Task with ID %s does not exists." % args[0]] -         -        task.setResult(" ".join(args[1:])) -        return ["INFO: Result %s saved." % " ".join(args[1:])] - - -    def event_help(self, args): -        lines = ["The following commands are available:", -                 "add <package|packid> <links> [...] Adds link to package. (creates new package if it does not exist)", -                 "queue                       Shows all packages in the queue", -                 "collector                   Shows all packages in collector", -                 "del -p|-l <id> [...]        Deletes all packages|links with the ids specified", -                 "info <id>                   Shows info of the link with id <id>", -                 "packinfo <id>               Shows info of the package with id <id>", -                 "more                        Shows more info when the result was truncated", -                 "start                       Starts all downloads", -                 "stop                        Stops the download (but not abort active downloads)", -                 "push <id>                   Push package to queue", -                 "pull <id>                   Pull package from queue", -                 "status                      Show general download status", -                 "help                        Shows this help message"] -        return lines -         -         -class IRCError(Exception): -    def __init__(self, value): -        Exception.__init__(value) -        self.value = value -    def __str__(self): -        return repr(self.value) diff --git a/module/plugins/hooks/ImageTyperz.py b/module/plugins/hooks/ImageTyperz.py deleted file mode 100644 index 59b6334a7..000000000 --- a/module/plugins/hooks/ImageTyperz.py +++ /dev/null @@ -1,160 +0,0 @@ -# -*- coding: utf-8 -*- -""" -    This program is free software; you can redistribute it and/or modify -    it under the terms of the GNU General Public License as published by -    the Free Software Foundation; either version 3 of the License, -    or (at your option) any later version. - -    This program is distributed in the hope that it will be useful, -    but WITHOUT ANY WARRANTY; without even the implied warranty of -    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. -    See the GNU General Public License for more details. - -    You should have received a copy of the GNU General Public License -    along with this program; if not, see <http://www.gnu.org/licenses/>. - -    @author: mkaay, RaNaN, zoidberg -""" -from __future__ import with_statement - -from thread import start_new_thread -from pycurl import FORM_FILE, LOW_SPEED_TIME - -from module.network.RequestFactory import getURL, getRequest -from module.network.HTTPRequest import BadHeader - -from module.plugins.Hook import Hook -import re -from base64 import b64encode - -class ImageTyperzException(Exception): -    def __init__(self, err): -        self.err = err - -    def getCode(self): -        return self.err - -    def __str__(self): -        return "<ImageTyperzException %s>" % self.err - -    def __repr__(self): -        return "<ImageTyperzException %s>" % self.err - -class ImageTyperz(Hook): -    __name__ = "ImageTyperz" -    __version__ = "0.03" -    __description__ = """send captchas to ImageTyperz.com""" -    __config__ = [("activated", "bool", "Activated", True), -                  ("username", "str", "Username", ""), -                  ("passkey", "password", "Password", ""), -                  ("force", "bool", "Force IT even if client is connected", False)] -    __author_name__ = ("RaNaN", "zoidberg") -    __author_mail__ = ("RaNaN@pyload.org", "zoidberg@mujmail.cz") - -    SUBMIT_URL = "http://captchatypers.com/Forms/UploadFileAndGetTextNEW.ashx" -    RESPOND_URL = "http://captchatypers.com/Forms/SetBadImage.ashx" -    GETCREDITS_URL = "http://captchatypers.com/Forms/RequestBalance.ashx" - -    def setup(self): -        self.info = {} - -    def getCredits(self): -        response = getURL(self.GETCREDITS_URL, -                      post = {"action": "REQUESTBALANCE", -                              "username": self.getConfig("username"), -                              "password": self.getConfig("passkey")} -                      ) -                                                                          -        if response.startswith('ERROR'): -            raise ImageTyperzException(response) -             -        try: -            balance = float(response) -        except: -            raise ImageTyperzException("invalid response") -             -        self.logInfo("Account balance: $%s left" % response) -        return balance  - -    def submit(self, captcha, captchaType="file", match=None): -        req = getRequest() -        #raise timeout threshold -        req.c.setopt(LOW_SPEED_TIME, 80) -         -        try: -            #workaround multipart-post bug in HTTPRequest.py  -            if re.match("^[A-Za-z0-9]*$", self.getConfig("passkey")): -                multipart = True -                data = (FORM_FILE, captcha) -            else: -                multipart = False -                with open(captcha, 'rb') as f: -                    data = f.read() -                data = b64encode(data) -                 -            response = req.load(self.SUBMIT_URL, -                                post={ "action": "UPLOADCAPTCHA", -                                       "username": self.getConfig("username"), -                                       "password": self.getConfig("passkey"), -                                       "file": data}, -                                multipart = multipart) -        finally: -            req.close() - -        if response.startswith("ERROR"): -            raise ImageTyperzException(response) -        else: -            data = response.split('|') -            if len(data) == 2: -                ticket, result = data -            else: -                raise ImageTyperzException("Unknown response %s" % response)       -         -        return ticket, result - -    def newCaptchaTask(self, task): -        if "service" in task.data: -            return False -         -        if not task.isTextual(): -            return False - -        if not self.getConfig("username") or not self.getConfig("passkey"): -            return False - -        if self.core.isClientConnected() and not self.getConfig("force"): -            return False - -        if self.getCredits() > 0: -            task.handler.append(self) -            task.data['service'] = self.__name__ -            task.setWaiting(100) -            start_new_thread(self.processCaptcha, (task,)) - -        else: -            self.logInfo("Your %s account has not enough credits" % self.__name__) - -    def captchaInvalid(self, task): -        if task.data['service'] == self.__name__ and "ticket" in task.data: -            response = getURL(self.RESPOND_URL, -                              post={"action": "SETBADIMAGE", -                                    "username": self.getConfig("username"), -                                    "password": self.getConfig("passkey"), -                                    "imageid": task.data["ticket"]} -                              ) -             -            if response == "SUCCESS": -                self.logInfo("Bad captcha solution received, requested refund") -            else: -                self.logError("Bad captcha solution received, refund request failed", response)  - -    def processCaptcha(self, task): -        c = task.captchaFile -        try: -            ticket, result = self.submit(c) -        except ImageTyperzException, e: -            task.error = e.getCode() -            return - -        task.data["ticket"] = ticket -        task.setResult(result)
\ No newline at end of file diff --git a/module/plugins/hooks/LinkdecrypterCom.py b/module/plugins/hooks/LinkdecrypterCom.py deleted file mode 100644 index ac939afd9..000000000 --- a/module/plugins/hooks/LinkdecrypterCom.py +++ /dev/null @@ -1,54 +0,0 @@ -# -*- coding: utf-8 -*- -""" -    This program is free software; you can redistribute it and/or modify -    it under the terms of the GNU General Public License as published by -    the Free Software Foundation; either version 3 of the License, -    or (at your option) any later version. - -    This program is distributed in the hope that it will be useful, -    but WITHOUT ANY WARRANTY; without even the implied warranty of -    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. -    See the GNU General Public License for more details. - -    You should have received a copy of the GNU General Public License -    along with this program; if not, see <http://www.gnu.org/licenses/>. - -    @author: zoidberg -""" - -import re - -from module.plugins.Hook import Hook -from module.network.RequestFactory import getURL -from module.utils import remove_chars - -class LinkdecrypterCom(Hook): -    __name__ = "LinkdecrypterCom" -    __version__ = "0.14" -    __description__ = """linkdecrypter.com - regexp loader""" -    __config__ = [ ("activated", "bool", "Activated" , "True") ] -    __author_name__ = ("zoidberg") -     -    def coreReady(self): -        page = getURL("http://linkdecrypter.com/") -        m = re.search(r'<b>Supported</b>: <i>([^+<]*)', page) -        if not m: -            self.logError(_("Crypter list not found")) -            return -             -        online = m.group(1).split(', ')             -        builtin = [ name.lower() for name in self.core.pluginManager.crypterPlugins.keys() ] -        builtin.extend([ "downloadserienjunkiesorg" ]) -                -        online = [ crypter.replace(".", "\\.") for crypter in online if remove_chars(crypter, "-.") not in builtin ] -        if not online: -            self.logError(_("Crypter list is empty")) -            return -              -        regexp = r"https?://([^.]+\.)*?(%s)/.*" % "|".join(online) - -        dict = self.core.pluginManager.crypterPlugins[self.__name__] -        dict["pattern"] = regexp -        dict["re"] = re.compile(regexp) -         -        self.logDebug("REGEXP: " + regexp)
\ No newline at end of file diff --git a/module/plugins/hooks/MergeFiles.py b/module/plugins/hooks/MergeFiles.py deleted file mode 100644 index 02d343096..000000000 --- a/module/plugins/hooks/MergeFiles.py +++ /dev/null @@ -1,94 +0,0 @@ -# -*- coding: utf-8 -*- - -""" -    This program is free software; you can redistribute it and/or modify -    it under the terms of the GNU General Public License as published by -    the Free Software Foundation; either version 3 of the License, -    or (at your option) any later version. - -    This program is distributed in the hope that it will be useful, -    but WITHOUT ANY WARRANTY; without even the implied warranty of -    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. -    See the GNU General Public License for more details. - -    You should have received a copy of the GNU General Public License -    along with this program; if not, see <http://www.gnu.org/licenses/>. -     -    @author: and9000 -""" - -import os -import re -import sys -import traceback - -from os.path import join -from module.utils import save_join, fs_encode -from module.plugins.Hook import Hook - -BUFFER_SIZE = 4096 - -class MergeFiles(Hook): -    __name__ = "MergeFiles" -    __version__ = "0.1" -    __description__ = "Merges parts splitted with hjsplit" -    __config__ = [ -        ("activated" , "bool" , "Activated"  , "False"), -        ] -    __threaded__ = ["packageFinished"] -    __author_name__ = ("and9000") -    __author_mail__ = ("me@has-no-mail.com") - -    def setup(self): -        # nothing to do -        pass -         -    def packageFinished(self, pack): -        files = {} -        fid_dict = {} -        for fid, data in pack.getChildren().iteritems(): -            if re.search("\.[0-9]{3}$", data["name"]): -                if data["name"][:-4] not in files: -                    files[data["name"][:-4]] = [] -                files[data["name"][:-4]].append(data["name"]) -                files[data["name"][:-4]].sort() -                fid_dict[data["name"]] = fid -                 -        download_folder = self.core.config['general']['download_folder'] -                 -        if self.core.config['general']['folder_per_package']: -            download_folder = save_join(download_folder, pack.folder) - -        for name, file_list in files.iteritems(): -            self.core.log.info("Starting merging of %s" % name) -            final_file = open(join(download_folder, fs_encode(name)), "wb") - -            for splitted_file in file_list: -                self.core.log.debug("Merging part %s" % splitted_file) -                pyfile = self.core.files.getFile(fid_dict[splitted_file]) -                pyfile.setStatus("processing") -                try: -                    s_file = open(os.path.join(download_folder, splitted_file), "rb") -                    size_written = 0 -                    s_file_size = int(os.path.getsize(os.path.join(download_folder, splitted_file))) -                    while True: -                        f_buffer = s_file.read(BUFFER_SIZE) -                        if f_buffer: -                            final_file.write(f_buffer) -                            size_written += BUFFER_SIZE -                            pyfile.setProgress((size_written*100)/s_file_size) -                        else: -                            break -                    s_file.close() -                    self.core.log.debug("Finished merging part %s" % splitted_file) -                except Exception, e: -                    print traceback.print_exc() -                finally: -                    pyfile.setProgress(100) -                    pyfile.setStatus("finished") -                    pyfile.release() -                     -            final_file.close() -            self.core.log.info("Finished merging of %s" % name) -                 - diff --git a/module/plugins/hooks/MultiHome.py b/module/plugins/hooks/MultiHome.py deleted file mode 100644 index f15148538..000000000 --- a/module/plugins/hooks/MultiHome.py +++ /dev/null @@ -1,82 +0,0 @@ -# -*- coding: utf-8 -*- - -""" -    This program is free software; you can redistribute it and/or modify -    it under the terms of the GNU General Public License as published by -    the Free Software Foundation; either version 3 of the License, -    or (at your option) any later version. - -    This program is distributed in the hope that it will be useful, -    but WITHOUT ANY WARRANTY; without even the implied warranty of -    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. -    See the GNU General Public License for more details. - -    You should have received a copy of the GNU General Public License -    along with this program; if not, see <http://www.gnu.org/licenses/>. -     -    @author: mkaay -""" - -from module.plugins.Hook import Hook -from time import time - -class MultiHome(Hook): -    __name__ = "MultiHome" -    __version__ = "0.1" -    __description__ = """ip address changer""" -    __config__ = [ ("activated", "bool", "Activated" , "False"), -                   ("interfaces", "str", "Interfaces" , "None") ] -    __author_name__ = ("mkaay") -    __author_mail__ = ("mkaay@mkaay.de") -     -    def setup(self): -        self.register = {} -        self.interfaces = [] -        self.parseInterfaces(self.getConfig("interfaces").split(";")) -        if not self.interfaces: -            self.parseInterfaces([self.config["download"]["interface"]]) -            self.setConfig("interfaces", self.toConfig()) -     -    def toConfig(self): -        return ";".join([i.adress for i in self.interfaces]) -     -    def parseInterfaces(self, interfaces): -        for interface in interfaces: -            if not interface or str(interface).lower() == "none": -                continue -            self.interfaces.append(Interface(interface)) -     -    def coreReady(self): -        requestFactory = self.core.requestFactory -        oldGetRequest = requestFactory.getRequest -        def getRequest(pluginName, account=None): -            iface = self.bestInterface(pluginName, account) -            if iface: -                iface.useFor(pluginName, account) -                requestFactory.iface = lambda: iface.adress -                self.log.debug("Multihome: using address: "+iface.adress) -            return oldGetRequest(pluginName, account) -        requestFactory.getRequest = getRequest -     -    def bestInterface(self, pluginName, account): -        best = None -        for interface in self.interfaces: -            if not best or interface.lastPluginAccess(pluginName, account) < best.lastPluginAccess(pluginName, account): -                best = interface -        return best - -class Interface(object): -    def __init__(self, adress): -        self.adress = adress -        self.history = {} -     -    def lastPluginAccess(self, pluginName, account): -        if (pluginName, account) in self.history: -            return self.history[(pluginName, account)] -        return 0 -     -    def useFor(self, pluginName, account): -        self.history[(pluginName, account)] = time() -     -    def __repr__(self): -        return "<Interface - %s>" % self.adress diff --git a/module/plugins/hooks/MultishareCz.py b/module/plugins/hooks/MultishareCz.py deleted file mode 100644 index a00c6cb2b..000000000 --- a/module/plugins/hooks/MultishareCz.py +++ /dev/null @@ -1,40 +0,0 @@ -# -*- coding: utf-8 -*- - -from module.network.RequestFactory import getURL -from module.plugins.internal.MultiHoster import MultiHoster -import re - -def getConfigSet(option): -    s = set(option.lower().split('|')) -    s.discard(u'') -    return s - -class MultishareCz(MultiHoster): -    __name__ = "MultishareCz" -    __version__ = "0.03" -    __type__ = "hook" -    __config__ = [("activated", "bool", "Activated", "False"), -        ("hosterListMode", "all;listed;unlisted", "Use for hosters (if supported)", "all"), -        ("hosterList", "str", "Hoster list (comma separated)", "uloz.to")] -    __description__ = """MultiShare.cz hook plugin""" -    __author_name__ = ("zoidberg") -    __author_mail__ = ("zoidberg@mujmail.cz") - -    replacements = [("share-rapid.cz", "sharerapid.com")] -    HOSTER_PATTERN = r'<img class="logo-shareserveru"[^>]*?alt="([^"]+)"></td>\s*<td class="stav">[^>]*?alt="OK"' - -    def getHoster(self): - -        page = getURL("http://www.multishare.cz/monitoring/") -        hosters = set(h.lower().strip() for h in re.findall(self.HOSTER_PATTERN, page))  -         -        configMode = self.getConfig('hosterListMode') -        if configMode in ("listed", "unlisted"): -            configList = set(self.getConfig('hosterList').strip().lower().replace('|',',').replace(';',',').split(',')) -            configList.discard(u'') -            if configMode == "listed": -                hosters &= configList -            elif configMode == "unlisted": -                hosters -= configList -         -        return list(hosters)
\ No newline at end of file diff --git a/module/plugins/hooks/Premium4Me.py b/module/plugins/hooks/Premium4Me.py deleted file mode 100644 index fc3ce2343..000000000 --- a/module/plugins/hooks/Premium4Me.py +++ /dev/null @@ -1,46 +0,0 @@ -# -*- coding: utf-8 -*-
 -
 -from module.network.RequestFactory import getURL
 -from module.plugins.internal.MultiHoster import MultiHoster
 -
 -class Premium4Me(MultiHoster):
 -    __name__ = "Premium4Me"
 -    __version__ = "0.02"
 -    __type__ = "hook"
 -
 -    __config__ = [("activated", "bool", "Activated", "False"),
 -        ("hosterListMode", "all;listed;unlisted", "Use for downloads from supported hosters:", "all"),
 -        ("hosterList", "str", "Hoster list (comma separated)", "")]
 -    __description__ = """premium4.me hook plugin"""
 -    __author_name__ = ("RaNaN", "zoidberg")
 -    __author_mail__ = ("RaNaN@pyload.org", "zoidberg@mujmail.cz")
 -
 -    replacements = [("freakshare.net", "freakshare.com")]
 -
 -    def getHoster(self):
 -
 -        page = getURL("http://premium4.me/api/hosters.php?authcode=%s" % self.account.authcode)
 -        hosters = set([x.strip() for x in page.replace("\"", "").split(";")])
 -        
 -        configMode = self.getConfig('hosterListMode')
 -        if configMode in ("listed", "unlisted"):
 -            configList = set(self.getConfig('hosterList').strip().lower().replace(',','|').split('|'))
 -            configList.discard(u'')
 -            if configMode == "listed":
 -                hosters &= configList
 -            elif configMode == "unlisted":
 -                hosters -= configList
 -        
 -        return list(hosters)
 -
 -    def coreReady(self):
 -
 -        self.account = self.core.accountManager.getAccountPlugin("Premium4Me")
 -
 -        user = self.account.selectAccount()[0]
 -
 -        if not user:
 -            self.logError(_("Please add your premium4.me account first and restart pyLoad"))
 -            return
 -
 -        return MultiHoster.coreReady(self)
\ No newline at end of file diff --git a/module/plugins/hooks/PremiumizeMe.py b/module/plugins/hooks/PremiumizeMe.py deleted file mode 100644 index 3825e9219..000000000 --- a/module/plugins/hooks/PremiumizeMe.py +++ /dev/null @@ -1,65 +0,0 @@ -from module.plugins.internal.MultiHoster import MultiHoster - -from module.common.json_layer      import json_loads -from module.network.RequestFactory import getURL - -class PremiumizeMe(MultiHoster): -    __name__ = "PremiumizeMe" -    __version__ = "0.1" -    __type__ = "hook" -    __description__ = """Premiumize.Me hook plugin""" - -    __config__ = [("activated", "bool", "Activated", "False"), -                  ("hosterListMode", "all;listed;unlisted", "Use for hosters (if supported):", "all"),  -                  ("hosterList", "str", "Hoster list (comma separated)", "")] - -    __author_name__ = ("Florian Franzen") -    __author_mail__ = ("FlorianFranzen@gmail.com") - -    replacements = [("freakshare.net", "freakshare.com")] - -    interval = 0 # Disable periodic calls, we dont use them anyway -     -    def getHoster(self):      -        # If no accounts are available there will be no hosters available -        if not self.account or not self.account.canUse(): -            return [] -         -        # Get account data -        (user, data) = self.account.selectAccount() -         -        # Get supported hosters list from premiumize.me using the json API v1 (see https://secure.premiumize.me/?show=api) -        answer = getURL("https://api.premiumize.me/pm-api/v1.php?method=hosterlist¶ms[login]=%s¶ms[pass]=%s" % (user, data['password'])) -        data = json_loads(answer) -         -         -        # If account is not valid thera are no hosters available -        if data['status'] != 200: -            return [] -         -        # Extract hosters from json file  -        hosters = set(data['result']['hosterlist']) -     -                 -        # Read config to check if certain hosters should not be handled -        configMode = self.getConfig('hosterListMode') -        if configMode in ("listed", "unlisted"): -            configList = set(self.getConfig('hosterList').strip().lower().replace('|',',').replace(';',',').split(',')) -            configList.discard(u'') -            if configMode == "listed": -                hosters &= configList -            else: -                hosters -= configList -         -        return list(hosters)       -             -    def coreReady(self): -        # Get account plugin and check if there is a valid account available -        self.account = self.core.accountManager.getAccountPlugin("PremiumizeMe")      -        if not self.account.canUse(): -            self.account = None -            self.logError(_("Please add a valid premiumize.me account first and restart pyLoad.")) -            return -                   -        # Run the overwriten core ready which actually enables the multihoster hook  -        return MultiHoster.coreReady(self)
\ No newline at end of file diff --git a/module/plugins/hooks/RealdebridCom.py b/module/plugins/hooks/RealdebridCom.py deleted file mode 100644 index bd3179673..000000000 --- a/module/plugins/hooks/RealdebridCom.py +++ /dev/null @@ -1,36 +0,0 @@ -# -*- coding: utf-8 -*- - -from module.network.RequestFactory import getURL -from module.plugins.internal.MultiHoster import MultiHoster - -class RealdebridCom(MultiHoster): -    __name__ = "RealdebridCom" -    __version__ = "0.41" -    __type__ = "hook" - -    __config__ = [("activated", "bool", "Activated", "False"), -                  ("https", "bool", "Enable HTTPS", "False"), -                  ("hosterListMode", "all;listed;unlisted", "Use for hosters (if supported):", "all"), -                  ("hosterList", "str", "Hoster list (comma separated)", "")] -    __description__ = """Real-Debrid.com hook plugin""" -    __author_name__ = ("Devirex, Hazzard") -    __author_mail__ = ("naibaf_11@yahoo.de") - -    replacements = [("freakshare.net", "freakshare.com")] - -    def getHoster(self): -        https = "https" if self.getConfig("https") else "http" -        page = getURL(https + "://real-debrid.com/api/hosters.php").replace("\"","").strip() - -        hosters = set([x.strip() for x in page.split(",") if x.strip()]) -         -        configMode = self.getConfig('hosterListMode') -        if configMode in ("listed", "unlisted"): -            configList = set(self.getConfig('hosterList').strip().lower().replace('|',',').replace(';',',').split(',')) -            configList.discard(u'') -            if configMode == "listed": -                hosters &= configList -            else: -                hosters -= configList -         -        return list(hosters) diff --git a/module/plugins/hooks/RehostTo.py b/module/plugins/hooks/RehostTo.py deleted file mode 100644 index b16987f5c..000000000 --- a/module/plugins/hooks/RehostTo.py +++ /dev/null @@ -1,39 +0,0 @@ -# -*- coding: utf-8 -*- - -from module.network.RequestFactory import getURL -from module.plugins.internal.MultiHoster import MultiHoster - -class RehostTo(MultiHoster): -    __name__ = "RehostTo" -    __version__ = "0.41" -    __type__ = "hook" - -    __config__ = [("activated", "bool", "Activated", "False")] - -    __description__ = """rehost.to hook plugin""" -    __author_name__ = ("RaNaN") -    __author_mail__ = ("RaNaN@pyload.org") - -    replacements = [("freakshare.net", "freakshare.com")] - -    def getHoster(self): - -        page = getURL("http://rehost.to/api.php?cmd=get_supported_och_dl&long_ses=%s" % self.long_ses) -        return [x.strip() for x in page.replace("\"", "").split(",")] - - -    def coreReady(self): - -        self.account = self.core.accountManager.getAccountPlugin("RehostTo") - -        user = self.account.selectAccount()[0] - -        if not user: -            self.log.error("Rehost.to: "+ _("Please add your rehost.to account first and restart pyLoad")) -            return - -        data = self.account.getAccountInfo(user) -        self.ses = data["ses"] -        self.long_ses = data["long_ses"] - -        return MultiHoster.coreReady(self) diff --git a/module/plugins/hooks/UpdateManager.py b/module/plugins/hooks/UpdateManager.py deleted file mode 100644 index ce75399c5..000000000 --- a/module/plugins/hooks/UpdateManager.py +++ /dev/null @@ -1,194 +0,0 @@ -# -*- coding: utf-8 -*- - -""" -    This program is free software; you can redistribute it and/or modify -    it under the terms of the GNU General Public License as published by -    the Free Software Foundation; either version 3 of the License, -    or (at your option) any later version. - -    This program is distributed in the hope that it will be useful, -    but WITHOUT ANY WARRANTY; without even the implied warranty of -    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. -    See the GNU General Public License for more details. - -    You should have received a copy of the GNU General Public License -    along with this program; if not, see <http://www.gnu.org/licenses/>. - -    @author: RaNaN -""" - -import sys -import re -from os import stat -from os.path import join, exists -from time import time - -from module.ConfigParser import IGNORE -from module.network.RequestFactory import getURL -from module.plugins.Hook import threaded, Expose, Hook - -class UpdateManager(Hook): -    __name__ = "UpdateManager" -    __version__ = "0.12" -    __description__ = """checks for updates""" -    __config__ = [("activated", "bool", "Activated", "True"), -        ("interval", "int", "Check interval in minutes", "360"), -        ("debug", "bool", "Check for plugin changes when in debug mode", False)] -    __author_name__ = ("RaNaN") -    __author_mail__ = ("ranan@pyload.org") - -    @property -    def debug(self): -        return self.core.debug and self.getConfig("debug") - - -    def setup(self): -        if self.debug: -            self.logDebug("Monitoring file changes") -            self.interval = 4 -            self.last_check = 0 #timestamp of updatecheck -            self.old_periodical = self.periodical -            self.periodical = self.checkChanges -            self.mtimes = {}  #recordes times -        else: -            self.interval = self.getConfig("interval") * 60 - -        self.updated = False -        self.reloaded = True - -        self.info = {"pyload": False, "plugins": False} - -    @threaded -    def periodical(self): -        update = self.checkForUpdate() -        if update: -            self.info["pyload"] = True -        else: -            self.log.info(_("No Updates for pyLoad")) -            self.checkPlugins() - -        if self.updated and not self.reloaded: -            self.info["plugins"] = True -            self.log.info(_("*** Plugins have been updated, please restart pyLoad ***")) -        elif self.updated and self.reloaded: -            self.log.info(_("Plugins updated and reloaded")) -            self.updated = False -        else: -            self.log.info(_("No plugin updates available")) - -    @Expose -    def recheckForUpdates(self): -        """recheck if updates are available""" -        self.periodical() - -    def checkForUpdate(self): -        """checks if an update is available""" - -        try: -            version_check = getURL("http://get.pyload.org/check/%s/" % self.core.api.getServerVersion()) -            if version_check == "": -                return False -            else: -                self.log.info(_("***  New pyLoad Version %s available  ***") % version_check) -                self.log.info(_("***  Get it here: http://pyload.org/download  ***")) -                return True -        except: -            self.log.warning(_("Not able to connect server for updates")) -            return False - - -    def checkPlugins(self): -        """ checks for plugins updates""" - -        # plugins were already updated -        if self.info["plugins"]: return - -        try: -            updates = getURL("http://get.pyload.org/plugins/check/") -        except: -            self.log.warning(_("Not able to connect server for updates")) -            return False - -        updates = updates.splitlines() -        reloads = [] - -        vre = re.compile(r'__version__.*=.*("|\')([0-9.]+)') - -        for plugin in updates: -            path, version = plugin.split(":") -            prefix, filename = path.split("/") - -            if filename.endswith(".pyc"): -                name = filename[:filename.find("_")] -            else: -                name = filename.replace(".py", "") - -	    #TODO: obsolete -            if prefix.endswith("s"): -                type = prefix[:-1] -            else: -                type = prefix - -            plugins = getattr(self.core.pluginManager, "%sPlugins" % type) - -            if name in plugins: -                if float(plugins[name]["v"]) >= float(version): -                    continue - -            if name in IGNORE or (type, name) in IGNORE: -                continue - -            self.log.info(_("New version of %(type)s|%(name)s : %(version).2f") % { -                "type": type, -                "name": name, -                "version": float(version) -            }) - -            try: -                content = getURL("http://get.pyload.org/plugins/get/" + path) -            except Exception, e: -                self.logWarning(_("Error when updating %s") % filename, str(e)) -                continue - -            m = vre.search(content) -            if not m or m.group(2) != version: -                self.logWarning(_("Error when updating %s") % name, _("Version mismatch")) -                continue - -            f = open(join("userplugins", prefix, filename), "wb") -            f.write(content) -            f.close() -            self.updated = True - -            reloads.append((prefix, name)) - -        self.reloaded = self.core.pluginManager.reloadPlugins(reloads) - -    def checkChanges(self): - -        if self.last_check + self.getConfig("interval") * 60 < time(): -            self.old_periodical() -            self.last_check = time() - -        modules = filter( -            lambda m: m and (m.__name__.startswith("module.plugins.") or m.__name__.startswith("userplugins.")) and m.__name__.count(".") >= 2, -            sys.modules.itervalues()) - -        reloads = [] - -        for m in modules: -            root, type, name = m.__name__.rsplit(".", 2) -            id = (type, name) -            if type in self.core.pluginManager.plugins: -                f = m.__file__.replace(".pyc", ".py") -                if not exists(f): continue - -                mtime = stat(f).st_mtime - -                if id not in self.mtimes: -                    self.mtimes[id] = mtime -                elif self.mtimes[id] < mtime: -                    reloads.append(id) -                    self.mtimes[id] = mtime - -        self.core.pluginManager.reloadPlugins(reloads) diff --git a/module/plugins/hooks/XFileSharingPro.py b/module/plugins/hooks/XFileSharingPro.py deleted file mode 100644 index 3981db2d0..000000000 --- a/module/plugins/hooks/XFileSharingPro.py +++ /dev/null @@ -1,74 +0,0 @@ -# -*- coding: utf-8 -*- - -from module.plugins.Hook import Hook -import re - -class XFileSharingPro(Hook): -    __name__ = "XFileSharingPro" -    __version__ = "0.03" -    __type__ = "hook" -    __config__ = [ ("activated" , "bool" , "Activated"  , "True"), -                   ("loadDefault", "bool", "Include default (built-in) hoster list" , "True"), -                   ("includeList", "str", "Include hosters (comma separated)", ""), -                   ("excludeList", "str", "Exclude hosters (comma separated)", "") ] -    __description__ = """Hoster URL pattern loader for the generic XFileSharingPro plugin""" -    __author_name__ = ("zoidberg") -    __author_mail__ = ("zoidberg@mujmail.cz") -           -    def coreReady(self): -        self.loadPattern() -       -    def loadPattern(self):          -        hosterList = self.getConfigSet('includeList') -        excludeList = self.getConfigSet('excludeList')          -         -        if self.getConfig('loadDefault'):         -            hosterList |= set(( -            #WORKING HOSTERS: -            "azsharing.com", "banashare.com", "fileband.com", "kingsupload.com", "migahost.com", "ryushare.com", "xfileshare.eu", -            #NOT TESTED: -            "aieshare.com", "amonshare.com", "asixfiles.com",    -            "bebasupload.com", "boosterking.com", "buckshare.com", "bulletupload.com", "crocshare.com", "ddlanime.com", "divxme.com",  -            "dopeshare.com", "downupload.com", "eyesfile.com", "eyvx.com", "fik1.com", "file4safe.com", "file4sharing.com",  -            "fileforth.com", "filemade.com", "filemak.com", "fileplaygroud.com", "filerace.com", "filestrack.com",  -            "fileupper.com", "filevelocity.com", "fooget.com", "4bytez.com", "freefilessharing.com", "glumbouploads.com", "grupload.com",  -            "heftyfile.com", "hipfile.com", "host4desi.com", "hulkshare.com", "idupin.com", "imageporter.com", "isharefast.com",  -            "jalurcepat.com", "laoupload.com", "linkzhost.com", "loombo.com", "maknyos.com",  -            "mlfat4arab.com", "movreel.com", "netuploaded.com", "ok2upload.com", "180upload.com", "1hostclick.com", "ovfile.com",  -            "putshare.com", "pyramidfiles.com", "q4share.com", "queenshare.com", "ravishare.com", "rockdizfile.com", "sendmyway.com",  -            "share76.com", "sharebeast.com", "sharehut.com", "sharerun.com", "shareswift.com", "sharingonline.com", "6ybh-upload.com",  -            "skipfile.com", "spaadyshare.com", "space4file.com", "speedoshare.com", "uploadbaz.com", "uploadboost.com", "uploadc.com",  -            "uploaddot.com", "uploadfloor.com", "uploadic.com", "uploadville.com", "uptobox.com", "vidbull.com", "zalaa.com",  -            "zomgupload.com", "kupload.org", "movbay.org", "multishare.org", "omegave.org", "toucansharing.org", "uflinq.org", -            "banicrazy.info", "flowhot.info", "upbrasil.info", "shareyourfilez.biz", "bzlink.us", "cloudcache.cc", "fileserver.cc" -            "farshare.to", "kingshare.to", "filemaze.ws", "filehost.ws", "goldfile.eu", "filestock.ru", "moidisk.ru" -            "4up.me", "kfiles.kz", "odsiebie.pl", "upchi.co.il", "upit.in", "verzend.be" -            )) -             -            #NOT WORKING: -            """ -            """                 -               -        hosterList -= (excludeList) -        hosterList -= set(('', u'')) -         -        if not hosterList: -            self.unload() -            return -                                             -        regexp = r"http://(?:[^/]*\.)?(%s)/\w{12}" % ("|".join(sorted(hosterList)).replace('.','\.')) -        #self.logDebug(regexp) -         -        dict = self.core.pluginManager.hosterPlugins['XFileSharingPro'] -        dict["pattern"] = regexp -        dict["re"] = re.compile(regexp) -        self.logDebug("Pattern loaded - handling %d hosters" % len(hosterList)) -         -    def getConfigSet(self, option): -        s = self.getConfig(option).lower().replace('|',',').replace(';',',') -        return set([x.strip() for x in s.split(',')]) -         -    def unload(self): -        dict = self.core.pluginManager.hosterPlugins['XFileSharingPro'] -        dict["pattern"] = r"^unmatchable$" -        dict["re"] = re.compile(r"^unmatchable$")
\ No newline at end of file diff --git a/module/plugins/hooks/XMPPInterface.py b/module/plugins/hooks/XMPPInterface.py deleted file mode 100644 index a96adf524..000000000 --- a/module/plugins/hooks/XMPPInterface.py +++ /dev/null @@ -1,251 +0,0 @@ -# -*- coding: utf-8 -*- - -""" -    This program is free software; you can redistribute it and/or modify -    it under the terms of the GNU General Public License as published by -    the Free Software Foundation; either version 3 of the License, -    or (at your option) any later version. - -    This program is distributed in the hope that it will be useful, -    but WITHOUT ANY WARRANTY; without even the implied warranty of -    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. -    See the GNU General Public License for more details. - -    You should have received a copy of the GNU General Public License -    along with this program; if not, see <http://www.gnu.org/licenses/>. -     -    @author: RaNaN -    @interface-version: 0.2 -""" - -from pyxmpp import streamtls -from pyxmpp.all import JID, Message -from pyxmpp.jabber.client import JabberClient -from pyxmpp.interface import implements -from pyxmpp.interfaces import * - -from module.plugins.hooks.IRCInterface import IRCInterface - -class XMPPInterface(IRCInterface, JabberClient): -    __name__ = "XMPPInterface" -    __version__ = "0.1" -    __description__ = """connect to jabber and let owner perform different tasks""" -    __config__ = [("activated", "bool", "Activated", "False"), -            ("jid", "str", "Jabber ID", "user@exmaple-jabber-server.org"), -            ("pw", "str", "Password", ""), -            ("tls", "bool", "Use TLS", False), -            ("owners", "str", "List of JIDs accepting commands from", "me@icq-gateway.org;some@msn-gateway.org"), -            ("info_file", "bool", "Inform about every file finished", "False"), -            ("info_pack", "bool", "Inform about every package finished", "True"), -            ("captcha", "bool", "Send captcha requests", "True")] -    __author_name__ = ("RaNaN") -    __author_mail__ = ("RaNaN@pyload.org") - -    implements(IMessageHandlersProvider) - -    def __init__(self, core, manager): -        IRCInterface.__init__(self, core, manager) - -        self.jid = JID(self.getConfig("jid")) -        password = self.getConfig("pw") - -        # if bare JID is provided add a resource -- it is required -        if not self.jid.resource: -            self.jid = JID(self.jid.node, self.jid.domain, "pyLoad") - -        if self.getConfig("tls"): -            tls_settings = streamtls.TLSSettings(require=True, verify_peer=False) -            auth = ("sasl:PLAIN", "sasl:DIGEST-MD5") -        else: -            tls_settings = None -            auth = ("sasl:DIGEST-MD5", "digest") - -        # setup client with provided connection information -        # and identity data -        JabberClient.__init__(self, self.jid, password, -                              disco_name="pyLoad XMPP Client", disco_type="bot", -                              tls_settings=tls_settings, auth_methods=auth) - -        self.interface_providers = [ -            VersionHandler(self), -            self, -            ] - -    def coreReady(self): -        self.new_package = {} - -        self.start() - -    def packageFinished(self, pypack): -        try: -            if self.getConfig("info_pack"): -                self.announce(_("Package finished: %s") % pypack.name) -        except: -            pass - -    def downloadFinished(self, pyfile): -        try: -            if self.getConfig("info_file"): -                self.announce( -                    _("Download finished: %(name)s @ %(plugin)s") % {"name": pyfile.name, "plugin": pyfile.pluginname}) -        except: -            pass - -    def run(self): -        # connect to IRC etc. -        self.connect() -        try: -            self.loop() -        except Exception, ex: -            self.core.log.error("pyLoad XMPP: %s" % str(ex)) - -    def stream_state_changed(self, state, arg): -        """This one is called when the state of stream connecting the component -        to a server changes. This will usually be used to let the user -        know what is going on.""" -        self.log.debug("pyLoad XMPP: *** State changed: %s %r ***" % (state, arg)) - -    def disconnected(self): -        self.log.debug("pyLoad XMPP: Client was disconnected") - -    def stream_closed(self, stream): -        self.log.debug("pyLoad XMPP: Stream was closed | %s" % stream) - -    def stream_error(self, err): -        self.log.debug("pyLoad XMPP: Stream Error: %s" % err) - -    def get_message_handlers(self): -        """Return list of (message_type, message_handler) tuples. - -        The handlers returned will be called when matching message is received -        in a client session.""" -        return [ -                ("normal", self.message), -                                        ] - -    def message(self, stanza): -        """Message handler for the component.""" -        subject = stanza.get_subject() -        body = stanza.get_body() -        t = stanza.get_type() -        self.log.debug(u'pyLoad XMPP: Message from %s received.' % (unicode(stanza.get_from(), ))) -        self.log.debug(u'pyLoad XMPP: Body: %s Subject: %s Type: %s' % (body, subject, t)) - -        if t == "headline": -            # 'headline' messages should never be replied to -            return True -        if subject: -            subject = u"Re: " + subject - -        to_jid = stanza.get_from() -        from_jid = stanza.get_to() - -        #j = JID() -        to_name = to_jid.as_utf8() -        from_name = from_jid.as_utf8() - -        names = self.getConfig("owners").split(";") - -        if to_name in names or to_jid.node + "@" + to_jid.domain in names: -            messages = [] - -            trigger = "pass" -            args = None - -            try: -                temp = body.split() -                trigger = temp[0] -                if len(temp) > 1: -                    args = temp[1:] -            except: -                pass - -            handler = getattr(self, "event_%s" % trigger, self.event_pass) -            try: -                res = handler(args) -                for line in res: -                    m = Message( -                        to_jid=to_jid, -                        from_jid=from_jid, -                        stanza_type=stanza.get_type(), -                        subject=subject, -                        body=line) - -                    messages.append(m) -            except Exception, e: -                self.log.error("pyLoad XMPP: " + repr(e)) - -            return messages - -        else: -            return True - -    def response(self, msg, origin=""): -        return self.announce(msg) - -    def announce(self, message): -        """ send message to all owners""" -        for user in self.getConfig("owners").split(";"): -            self.log.debug("pyLoad XMPP: Send message to %s" % user) - -            to_jid = JID(user) - -            m = Message(from_jid=self.jid, -                        to_jid=to_jid, -                        stanza_type="chat", -                        body=message) - -            stream = self.get_stream() -            if not stream: -                self.connect() -                stream = self.get_stream() - -            stream.send(m) - -    def beforeReconnecting(self, ip): -        self.disconnect() - -    def afterReconnecting(self, ip): -        self.connect() - - -class VersionHandler(object): -    """Provides handler for a version query. -     -    This class will answer version query and announce 'jabber:iq:version' namespace -    in the client's disco#info results.""" - -    implements(IIqHandlersProvider, IFeaturesProvider) - -    def __init__(self, client): -        """Just remember who created this.""" -        self.client = client - -    def get_features(self): -        """Return namespace which should the client include in its reply to a -        disco#info query.""" -        return ["jabber:iq:version"] - -    def get_iq_get_handlers(self): -        """Return list of tuples (element_name, namespace, handler) describing -        handlers of <iq type='get'/> stanzas""" -        return [ -                ("query", "jabber:iq:version", self.get_version), -                                                                ] - -    def get_iq_set_handlers(self): -        """Return empty list, as this class provides no <iq type='set'/> stanza handler.""" -        return [] - -    def get_version(self, iq): -        """Handler for jabber:iq:version queries. - -        jabber:iq:version queries are not supported directly by PyXMPP, so the -        XML node is accessed directly through the libxml2 API.  This should be -        used very carefully!""" -        iq = iq.make_result_response() -        q = iq.new_query("jabber:iq:version") -        q.newTextChild(q.ns(), "name", "Echo component") -        q.newTextChild(q.ns(), "version", "1.0") -        return iq -    
\ No newline at end of file diff --git a/module/plugins/hooks/ZeveraCom.py b/module/plugins/hooks/ZeveraCom.py deleted file mode 100644 index 46c752c21..000000000 --- a/module/plugins/hooks/ZeveraCom.py +++ /dev/null @@ -1,33 +0,0 @@ -# -*- coding: utf-8 -*- - -from module.network.RequestFactory import getURL -from module.plugins.internal.MultiHoster import MultiHoster - -class ZeveraCom(MultiHoster): -    __name__ = "ZeveraCom" -    __version__ = "0.01" -    __type__ = "hook" -    __config__ = [("activated", "bool", "Activated", "False"), -                  ("hosterListMode", "all;listed;unlisted", "Use for hosters (if supported)", "all"), -                  ("hosterList", "str", "Hoster list (comma separated)", "")] -    __description__ = """Real-Debrid.com hook plugin""" -    __author_name__ = ("Devirex, Hazzard") -    __author_mail__ = ("naibaf_11@yahoo.de") - -    replacements = [("freakshare.net", "freakshare.com"), ("2shared.com", "twoshared.com"), ("4shared.com", "fourshared.com"), -                    ("easy-share.com", "crocko.com"), ("hellshare.com", "hellshare.cz")] - -    def getHoster(self): -        page = getURL("http://www.zevera.com/jDownloader.ashx?cmd=gethosters")         -        hosters = set([x.strip() for x in page.replace("\"", "").split(",")])    -         -        configMode = self.getConfig('hosterListMode') -        if configMode in ("listed", "unlisted"): -            configList = set(self.getConfig('hosterList').strip().lower().replace('|',',').replace(';',',').split(',')) -            configList.discard(u'') -            if configMode == "listed": -                hosters &= configList -            else: -                hosters -= configList -         -        return list(hosters)                                
\ No newline at end of file diff --git a/module/plugins/hooks/__init__.py b/module/plugins/hooks/__init__.py deleted file mode 100644 index e69de29bb..000000000 --- a/module/plugins/hooks/__init__.py +++ /dev/null | 
