summaryrefslogtreecommitdiffstats
path: root/module/plugins/hooks/ClickAndLoad.py
diff options
context:
space:
mode:
Diffstat (limited to 'module/plugins/hooks/ClickAndLoad.py')
-rw-r--r--module/plugins/hooks/ClickAndLoad.py166
1 files changed, 97 insertions, 69 deletions
diff --git a/module/plugins/hooks/ClickAndLoad.py b/module/plugins/hooks/ClickAndLoad.py
index 3c47d30ce..94a240d4c 100644
--- a/module/plugins/hooks/ClickAndLoad.py
+++ b/module/plugins/hooks/ClickAndLoad.py
@@ -1,91 +1,119 @@
# -*- 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.
+import socket
- 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.
+from threading import Thread, Lock
+from time import sleep
- You should have received a copy of the GNU General Public License
- along with this program; if not, see <http://www.gnu.org/licenses/>.
-"""
+from module.plugins.Hook import Hook, threaded
+
+
+def forward(source, destination):
+ string = ' '
+ while string:
+ string = source.recv(1024)
+ if string:
+ destination.sendall(string)
+ else:
+ destination.shutdown(socket.SHUT_WR)
-import socket
-import thread
-from module.plugins.Hook import Hook
+#: socket.create_connection wrapper for python 2.5
+def create_connection(address, timeout=object(), source_address=None):
+ try:
+ return socket.create_connection(address,
+ socket._GLOBAL_DEFAULT_TIMEOUT if type(timeout) == object else timeout,
+ source_address)
+
+ except SyntaxError:
+ """Connect to *address* and return the socket object.
+
+ Convenience function. Connect to *address* (a 2-tuple ``(host,
+ port)``) and return the socket object. Passing the optional
+ *timeout* parameter will set the timeout on the socket instance
+ before attempting to connect. If no *timeout* is supplied, the
+ global default timeout setting returned by :func:`getdefaulttimeout`
+ is used. If *source_address* is set it must be a tuple of (host, port)
+ for the socket to bind as a source address before making the connection.
+ An host of \'\' or port 0 tells the OS to use the default.
+ """
+
+ host, port = address
+ err = None
+ for res in getaddrinfo(host, port, 0, SOCK_STREAM):
+ af, socktype, proto, canonname, sa = res
+ sock = None
+ try:
+ sock = socket(af, socktype, proto)
+ if type(timeout) != object:
+ sock.settimeout(timeout)
+ if source_address:
+ sock.bind(source_address)
+ sock.connect(sa)
+ return sock
+
+ except socket.error, _:
+ err = _
+ if sock is not None:
+ sock.close()
+
+ if err is not None:
+ raise err
+ else:
+ raise socket.error("getaddrinfo returns an empty list")
class ClickAndLoad(Hook):
- __name__ = "ClickAndLoad"
- __version__ = "0.22"
- __type__ = "hook"
+ __name__ = "ClickAndLoad"
+ __type__ = "hook"
+ __version__ = "0.31"
- __config__ = [("activated", "bool", "Activated", True),
- ("extern", "bool", "Allow external link adding", False)]
+ __config__ = [("activated", "bool", "Activated" , True ),
+ ("port" , "int" , "Port" , 9666 ),
+ ("extern" , "bool", "Listen for requests coming from WAN (internet)", False)]
- __description__ = """Gives abillity to use jd's click and load. depends on webinterface"""
- __author_name__ = ("RaNaN", "mkaay")
- __author_mail__ = ("RaNaN@pyload.de", "mkaay@mkaay.de")
+ __description__ = """Click'N'Load hook plugin"""
+ __license__ = "GPLv3"
+ __authors__ = [("RaNaN", "RaNaN@pyload.de"),
+ ("Walter Purcaro", "vuolter@gmail.com")]
def coreReady(self):
- self.port = int(self.config['webinterface']['port'])
- if self.config['webinterface']['activated']:
- try:
- if self.getConfig("extern"):
- ip = "0.0.0.0"
- else:
- ip = "127.0.0.1"
+ if not self.config['webinterface']['activated']:
+ return
- thread.start_new_thread(proxy, (self, ip, self.port, 9666))
- except:
- self.logError("ClickAndLoad port already in use.")
+ ip = "0.0.0.0" if self.getConfig("extern") else "127.0.0.1"
+ webport = int(self.config['webinterface']['port'])
+ cnlport = self.getConfig('port')
+ self.proxy(ip, webport, cnlport)
-def proxy(self, *settings):
- thread.start_new_thread(server, (self,) + settings)
- lock = thread.allocate_lock()
- lock.acquire()
- lock.acquire()
+ @threaded
+ def proxy(self, ip, webport, cnlport):
+ self.manager.startThread(self.server, ip, webport, cnlport)
+ lock = 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.logWarning(_("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 server(self, ip, webport, cnlport):
+ try:
+ dock_socket = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
+ dock_socket.setsockopt(socket.SOL_SOCKET, socket.SO_REUSEADDR, 1)
+ dock_socket.bind((ip, cnlport))
+ dock_socket.listen(5)
-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)
+ while True:
+ server_socket = dock_socket.accept()[0]
+ client_socket = create_connection(("127.0.0.1", webport))
+
+ self.manager.startThread(forward, server_socket, client_socket)
+ self.manager.startThread(forward, client_socket, server_socket)
+
+ except socket.error, e:
+ self.logError(e)
+
+ finally:
+ dock_socket.close()