diff options
-rw-r--r-- | module/Api.py | 24 | ||||
-rw-r--r-- | module/HookManager.py | 42 | ||||
-rw-r--r-- | module/cli/AddPackage.py | 2 | ||||
-rw-r--r-- | module/plugins/Hook.py | 4 | ||||
-rw-r--r-- | module/plugins/crypter/SerienjunkiesOrg.py | 4 | ||||
-rw-r--r-- | module/plugins/hooks/ExternalScripts.py | 110 | ||||
-rw-r--r-- | module/plugins/hooks/UpdateManager.py | 29 | ||||
-rw-r--r-- | module/remote/thriftbackend/pyload.thrift | 2 | ||||
-rwxr-xr-x | pyLoadCli.py | 9 |
9 files changed, 132 insertions, 94 deletions
diff --git a/module/Api.py b/module/Api.py index d4dae3966..2f6200950 100644 --- a/module/Api.py +++ b/module/Api.py @@ -277,7 +277,8 @@ class Api(Iface): raise PackageDoesNotExists(pid) pdata = PackageData(data["id"], data["name"], data["folder"], data["site"], data["password"], - data["queue"], data["order"], data["priority"], fids=[int(x) for x in data["links"]]) + data["queue"], data["order"], data["priority"], + fids=[int(x) for x in data["links"]]) return pdata @@ -723,4 +724,23 @@ class Api(Iface): ret = self.core.hookManager.callRPC(plugin, func, args, parse) return str(ret) except Exception, e: - raise ServiceException(e.message)
\ No newline at end of file + raise ServiceException(e.message) + + def getAllInfo(self): + """Returns all information stored by hook plugins. Values are always strings + + :return: {"plugin": {"name": value } } + """ + return self.core.hookManager.getAllInfo() + + def getInfoByPlugin(self, plugin): + """Returns information stored by a specific plugin. + + :param plugin: pluginname + :return: dict of attr names mapped to value {"name": value} + """ + info = self.core.hookManager.getAllInfo() + if info.has_key(plugin): + return info[plugin] + else: + return {}
\ No newline at end of file diff --git a/module/HookManager.py b/module/HookManager.py index 29756f8c5..8b039683f 100644 --- a/module/HookManager.py +++ b/module/HookManager.py @@ -23,7 +23,6 @@ import traceback from threading import RLock from time import time - from module.PluginThread import HookThread from module.plugins.PluginManager import literal_eval @@ -47,8 +46,9 @@ class HookManager: res = func(*args) args[0].lock.release() return res + return new - + def try_catch(func): def new(*args): try: @@ -57,6 +57,7 @@ class HookManager: args[0].log.error(_("Error executing hooks: %s") % str(e)) if args[0].core.debug: traceback.print_exc() + return new @@ -73,14 +74,13 @@ class HookManager: if not args: args = tuple() if parse: args = tuple([literal_eval(x) for x in args]) - + plugin = self.pluginMap[plugin] f = getattr(plugin, func) return f(*args) def createIndex(self): - plugins = [] active = [] @@ -90,7 +90,7 @@ class HookManager: for pluginClass in self.core.pluginManager.getHookPlugins(): try: #hookClass = getattr(plugin, plugin.__name__) - + if self.core.config.getPlugin(pluginClass.__name__, "load"): plugin = pluginClass(self.core) plugins.append(plugin) @@ -100,12 +100,12 @@ class HookManager: else: deactive.append(pluginClass.__name__) - #self.log.info(_("%(name)s loaded, activated %(value)s") % {"name": pluginClass.__name__, "value": plugin.isActivated() }) + #self.log.info(_("%(name)s loaded, activated %(value)s") % {"name": pluginClass.__name__, "value": plugin.isActivated() }) else: #never reached, see plugin manager unloaded.append(pluginClass.__name__) except: - self.log.warning(_("Failed activating %(name)s") % {"name":pluginClass.__name__}) + self.log.warning(_("Failed activating %(name)s") % {"name": pluginClass.__name__}) if self.core.debug: traceback.print_exc() @@ -115,7 +115,7 @@ class HookManager: self.plugins = plugins - + def initPeriodical(self): def wrapPeriodical(plugin): plugin.lastCall = time() @@ -127,12 +127,12 @@ class HookManager: traceback.print_exc() self.core.scheduler.addJob(plugin.interval, wrapPeriodical, args=[plugin], threaded=False) - + for plugin in self.plugins: if plugin.isActivated() and plugin.interval >= 1: self.core.scheduler.addJob(0, wrapPeriodical, args=[plugin], threaded=False) - + @try_catch def coreReady(self): for plugin in self.plugins: @@ -142,47 +142,41 @@ class HookManager: @lock def downloadStarts(self, pyfile): - for plugin in self.plugins: if plugin.isActivated(): plugin.downloadStarts(pyfile) @lock def downloadFinished(self, pyfile): - for plugin in self.plugins: if plugin.isActivated(): if "downloadFinished" in plugin.__threaded__: self.startThread(plugin.downloadFinished, pyfile) else: plugin.downloadFinished(pyfile) - + @lock def packageFinished(self, package): - for plugin in self.plugins: if plugin.isActivated(): if "packageFinished" in plugin.__threaded__: self.startThread(plugin.packageFinished, package) else: plugin.packageFinished(package) - + @lock def beforeReconnecting(self, ip): - for plugin in self.plugins: plugin.beforeReconnecting(ip) - + @lock def afterReconnecting(self, ip): - for plugin in self.plugins: if plugin.isActivated(): plugin.afterReconnecting(ip) @lock def unrarFinished(self, folder, fname): - for plugin in self.plugins: plugin.unrarFinished(folder, fname) @@ -192,3 +186,13 @@ class HookManager: def activePlugins(self): """ returns all active plugins """ return [x for x in self.plugins if x.isActivated()] + + def getAllInfo(self): + """returns info stored by hook plugins""" + info = {} + for name, plugin in self.pluginMap.iteritems(): + if plugin.info: + #copy and convert so str + info[name] = dict([(x, str(y)) for x, y in plugin.info.iteritems()]) + return info + diff --git a/module/cli/AddPackage.py b/module/cli/AddPackage.py index ded08742b..a73401586 100644 --- a/module/cli/AddPackage.py +++ b/module/cli/AddPackage.py @@ -37,7 +37,7 @@ class AddPackage(Handler): self.setInput() elif inp == "END": #add package - self.client.addPackage(self.name, self.urls, 0) + self.client.addPackage(self.name, self.urls, 1) self.cli.reset() else: if inp.strip(): diff --git a/module/plugins/Hook.py b/module/plugins/Hook.py index 8a6355fcd..5e4b192ea 100644 --- a/module/plugins/Hook.py +++ b/module/plugins/Hook.py @@ -57,7 +57,9 @@ class Hook(): self.log = core.log self.config = core.config - self.interval = 60 + self.interval = 60 #: periodic call interval in seconds + + self.info = None #: Provide information in dict here, usable by API `getInfo` self.setup() diff --git a/module/plugins/crypter/SerienjunkiesOrg.py b/module/plugins/crypter/SerienjunkiesOrg.py index c907c5682..1e322a3a3 100644 --- a/module/plugins/crypter/SerienjunkiesOrg.py +++ b/module/plugins/crypter/SerienjunkiesOrg.py @@ -11,7 +11,7 @@ class SerienjunkiesOrg(Crypter): __name__ = "SerienjunkiesOrg" __type__ = "container" __pattern__ = r"http://.*?serienjunkies.org/.*?" - __version__ = "0.3" + __version__ = "0.31" __config__ = [ ("preferredHoster", "str", "preferred hoster" , "RapidshareCom,UploadedTo,NetloadIn,FilefactoryCom,FreakshareNet,FilebaseTo,MegauploadCom,HotfileCom,DepositfilesCom,EasyshareCom,KickloadCom"), ("changeName", "bool", "Take SJ.org episode name", "True") ] __description__ = """serienjunkies.org Container Plugin""" @@ -133,7 +133,7 @@ class SerienjunkiesOrg(Crypter): result = self.decryptCaptcha(str(captchaUrl), imgtype="png") sinp = form.find(attrs={"name":"s"}) - self.req.lastUrl = url + self.req.lastURL = url sj = self.req.load(str(url), post={'s': sinp["value"], 'c': result, 'action': "Download"}) soup = BeautifulSoup(sj) diff --git a/module/plugins/hooks/ExternalScripts.py b/module/plugins/hooks/ExternalScripts.py index 63ff2b170..bbf5acde3 100644 --- a/module/plugins/hooks/ExternalScripts.py +++ b/module/plugins/hooks/ExternalScripts.py @@ -18,98 +18,92 @@ @interface-version: 0.1 """ -from module.plugins.Hook import Hook import subprocess -from os import listdir -from os.path import join -import sys +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.1" + __version__ = "0.2" __description__ = """run external scripts""" - __config__ = [ ("activated", "bool", "Activated" , "True") ] + __config__ = [("activated", "bool", "Activated", "True")] __author_name__ = ("mkaay", "RaNaN", "spoob") __author_mail__ = ("mkaay@mkaay.de", "ranan@pyload.org", "spoob@pyload.org") - def __init__(self, core): - Hook.__init__(self, core) + + def setup(self): self.scripts = {} - script_folders = [join(pypath, 'scripts','download_preparing'), - join(pypath,'scripts','download_finished'), - join(pypath,'scripts','package_finished'), - join(pypath,'scripts','before_reconnect'), - join(pypath,'scripts','after_reconnect'), - join(pypath,'scripts','unrar_finished')] + folders = ['download_preparing', 'download_finished', 'package_finished', + 'before_reconnect', 'after_reconnect', 'unrar_finished'] + - folder = core.path("scripts") + for folder in folders: - self.core.check_file(folder, _("folders for scripts"), True) - self.core.check_file(script_folders, _("folders for scripts"), True) + 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 : %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) - f = lambda x: False if x.startswith("#") or x.endswith("~") else True - self.scripts = {'download_preparing': filter(f, listdir(join(folder, 'download_preparing'))), - 'download_finished': filter(f, listdir(join(folder, 'download_finished'))), - 'package_finished': filter(f, listdir(join(folder, 'package_finished'))), - 'before_reconnect': filter(f, listdir(join(folder, 'before_reconnect'))), - 'after_reconnect': filter(f, listdir(join(folder, 'after_reconnect'))), - 'unrar_finished': filter(f, listdir(join(folder, 'unrar_finished')))} + for f in listdir(path): + if f.startswith("#") or f.startswith(".") or f.startswith("_") or f.endswith("~") or f.endswith(".swp"): + continue - for script_type, script_name in self.scripts.iteritems(): - if script_name: - self.log.info("Installed %s Scripts: %s" % (script_type, ", ".join(script_name))) + if not access(join(path,f), X_OK): + self.logWarning(_("Script not executable: %s/%s") % (folder, f)) - #~ self.core.logger.info("Installed Scripts: %s" % str(self.scripts)) + self.scripts[folder].append(join(path, f)) - self.folder = folder + def callScript(self, script, *args): + try: + cmd = [script] + [str(x) if type(x) != basestring else x for x in args] + #output goes to pyload + out = subprocess.Popen(cmd, bufsize=-1) + out.wait() + except Exception, e: + self.logError(_("Error in %s: %s") % (basename(script), str(e))) def downloadStarts(self, pyfile): for script in self.scripts['download_preparing']: - try: - cmd = [join(self.folder, 'download_preparing', script), pyfile.pluginname, pyfile.url] - out = subprocess.Popen(cmd, stdout=subprocess.PIPE) - out.wait() - except: - pass + self.callScript(script, pyfile.pluginname, pyfile.url, pyfile.id) def downloadFinished(self, pyfile): for script in self.scripts['download_finished']: - try: - out = subprocess.Popen([join(self.folder, 'download_finished', script), pyfile.pluginname, pyfile.url, pyfile.name, join(self.core.config['general']['download_folder'], pyfile.package().folder, pyfile.name)], stdout=subprocess.PIPE) - except: - pass + 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'] if self.core.config.get("general", "folder_per_package"): - folder = join(folder.decode(sys.getfilesystemencoding()), pypack.folder.decode(sys.getfilesystemencoding())) + folder = save_join(folder. pypack.folder) - try: - out = subprocess.Popen([join(self.folder, 'package_finished', script), pypack.name, folder], stdout=subprocess.PIPE) - except: - pass + self.callScript(script, pypack.name, folder, pypack.id) def beforeReconnecting(self, ip): for script in self.scripts['before_reconnect']: - try: - out = subprocess.Popen([join(self.folder, 'before_reconnect', script), ip], stdout=subprocess.PIPE) - out.wait() - except: - pass + self.callScript(script, ip) def afterReconnecting(self, ip): for script in self.scripts['after_reconnect']: - try: - out = subprocess.Popen([join(self.folder, 'after_reconnect', script), ip], stdout=subprocess.PIPE) - except: - pass + self.callScript(script, ip) def unrarFinished(self, folder, fname): for script in self.scripts["unrar_finished"]: - try: - out = subprocess.Popen([join(self.folder, 'unrar_finished', script), folder, fname], stdout=subprocess.PIPE) - except: - pass - + self.callScript(script, folder, fname) diff --git a/module/plugins/hooks/UpdateManager.py b/module/plugins/hooks/UpdateManager.py index 026cd0c9f..10f50d1f0 100644 --- a/module/plugins/hooks/UpdateManager.py +++ b/module/plugins/hooks/UpdateManager.py @@ -17,6 +17,7 @@ @author: RaNaN @interface-version: 0.1 """ +import re from os.path import join from module.network.RequestFactory import getURL @@ -27,7 +28,7 @@ class UpdateManager(Hook): __version__ = "0.1" __description__ = """checks for updates""" __config__ = [("activated", "bool", "Activated", "True"), - ("interval", "int", "Check interval in minutes", "180")] + ("interval", "int", "Check interval in minutes", "360")] __author_name__ = ("RaNaN") __author_mail__ = ("ranan@pyload.org") @@ -36,12 +37,19 @@ class UpdateManager(Hook): self.updated = False self.reloaded = True + self.info = {"pyload": False, "plugins": False} + @threaded def periodical(self): update = self.checkForUpdate() - if not update: + 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")) @@ -59,7 +67,6 @@ class UpdateManager(Hook): try: version_check = getURL("http://get.pyload.org/check/%s/" % self.core.server_methods.get_server_version()) if version_check == "": - self.log.info(_("No Updates for pyLoad")) return False else: self.log.info(_("*** New pyLoad Version %s available ***") % version_check) @@ -81,6 +88,8 @@ class UpdateManager(Hook): updates = updates.splitlines() + vre = re.compile(r'__version__.*=.*("|\')([0-9.]+)') + for plugin in updates: path, version = plugin.split(":") prefix, name = path.split("/") @@ -107,11 +116,21 @@ class UpdateManager(Hook): "version": float(version) }) - content = getURL("http://get.pyload.org/plugins/get/" + path) + try: + content = getURL("http://get.pyload.org/plugins/get/" + path) + except: + self.logWarning(_("Error when updating %s") % name) + continue + + m = vre.search(content) + if not m or m.group(2) != version: + self.logWarning(_("Error when updating %s") % name) + continue + f = open(join("userplugins", prefix, name), "wb") f.write(content) f.close() self.updated = True self.reloaded = False - self.core.pluginManager.reloadPlugins()
\ No newline at end of file + self.core.pluginManager.reloadPlugins() diff --git a/module/remote/thriftbackend/pyload.thrift b/module/remote/thriftbackend/pyload.thrift index 07f36aec9..45d7f5eeb 100644 --- a/module/remote/thriftbackend/pyload.thrift +++ b/module/remote/thriftbackend/pyload.thrift @@ -277,7 +277,7 @@ service Pyload { //info // {plugin: {name: value}} map<PluginName, map<string,string>> getAllInfo(), - map<string, string> getInfoByPlugin(1: string plugin) + map<string, string> getInfoByPlugin(1: PluginName plugin) //scheduler diff --git a/pyLoadCli.py b/pyLoadCli.py index f572cf7e5..438be61aa 100755 --- a/pyLoadCli.py +++ b/pyLoadCli.py @@ -289,14 +289,14 @@ class Cli: print _("Please use this syntax: add <Package name> <link> <link2> ...") return - self.client.addPackage(args[0], args[1:], 0) + self.client.addPackage(args[0], args[1:], Destination.Queue) elif command == "add_coll": if len(args) < 2: print _("Please use this syntax: add <Package name> <link> <link2> ...") return - self.client.addPackage(args[0], args[1:], 1) + self.client.addPackage(args[0], args[1:], Destination.Collector) elif command == "del_file": self.client.deleteFiles([int(x) for x in args]) @@ -308,7 +308,7 @@ class Cli: elif command == "move": for pid in args: - pack = self.client.getPackageData(int(pid)) + pack = self.client.getPackageInfo(int(pid)) self.client.movePackage((pack.dest + 1) % 2, pack.pid) elif command == "pause": @@ -328,8 +328,7 @@ class Cli: print "Files restarted." elif command == "restart_package": for pid in args: - pack = self.client.getPackageData(int(pid)) - self.client.restartPackage(pack.pid) + self.client.restartPackage(int(pid)) print "Packages restarted." else: |