summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--module/gui/Collector.py2
-rw-r--r--module/plugins/decrypter/SerienjunkiesOrg.py1
-rw-r--r--module/web/ServerThread.py3
-rw-r--r--module/web/ajax/views.py52
-rwxr-xr-xmodule/web/manage.py27
-rw-r--r--module/web/media/default/js/jquery.form.js660
-rw-r--r--module/web/pyload/views.py49
-rwxr-xr-xmodule/web/run_unix.py21
-rw-r--r--module/web/settings.py2
-rw-r--r--module/web/templates/default/base.html19
-rw-r--r--module/web/templates/default/home.html3
-rw-r--r--module/web/templates/default/window.html7
-rwxr-xr-xpyLoadCli.py30
-rwxr-xr-xpyLoadCore.py38
14 files changed, 797 insertions, 117 deletions
diff --git a/module/gui/Collector.py b/module/gui/Collector.py
index 112eb1cd5..0aad5d1ba 100644
--- a/module/gui/Collector.py
+++ b/module/gui/Collector.py
@@ -19,8 +19,6 @@
from PyQt4.QtCore import *
from PyQt4.QtGui import *
-from time import sleep
-
from module.gui.Queue import ItemIterator
class PackageCollector(QObject):
diff --git a/module/plugins/decrypter/SerienjunkiesOrg.py b/module/plugins/decrypter/SerienjunkiesOrg.py
index 15bee52ac..7302f904e 100644
--- a/module/plugins/decrypter/SerienjunkiesOrg.py
+++ b/module/plugins/decrypter/SerienjunkiesOrg.py
@@ -1,7 +1,6 @@
# -*- coding: utf-8 -*-
import re
-from time import sleep
from module.Plugin import Plugin
from module.BeautifulSoup import BeautifulSoup
diff --git a/module/web/ServerThread.py b/module/web/ServerThread.py
index 8be3892b5..1276966ef 100644
--- a/module/web/ServerThread.py
+++ b/module/web/ServerThread.py
@@ -18,7 +18,6 @@ class WebServer(threading.Thread):
def run(self):
host = self.pycore.config['webinterface']['host']
port = self.pycore.config['webinterface']['port']
- command = ['python',join(self.pycore.path,"module","web","manage.py"), "runserver", "%s:%s" % (host,port)]
if not exists(join(self.pycore.path,"module","web","pyload.db")):
print "########## IMPORTANT ###########"
@@ -32,6 +31,7 @@ class WebServer(threading.Thread):
self.pycore.logger.info("Starting Webserver: %s:%s" % (host,port) )
if os.name == 'posix':
+ command = ['python',join(self.pycore.path,"module","web","run_unix.py"), "runserver", "%s:%s" % (host,port)]
self.p = Popen(command, close_fds=True, stderr=PIPE, stdin=PIPE, stdout=PIPE)
#os.system("python " + join(self.pycore.path,"module","web","manage.py runserver %s:%s" % (host,port)))
#@TODO: better would be real python code
@@ -41,6 +41,7 @@ class WebServer(threading.Thread):
while self.running:
sleep(1)
else:
+ command = ['python',join(self.pycore.path,"module","web","manage.py"), "runserver", "%s:%s" % (host,port)]
self.p = Popen(command, stderr=PIPE, stdin=PIPE, stdout=PIPE)
while self.running:
sleep(1)
diff --git a/module/web/ajax/views.py b/module/web/ajax/views.py
index b09a80581..952fbe2eb 100644
--- a/module/web/ajax/views.py
+++ b/module/web/ajax/views.py
@@ -1,16 +1,18 @@
# Create your views here.
+from os.path import join
+
+from django.conf import settings
+from django.core.serializers import json
from django.http import HttpResponse
from django.http import HttpResponseForbidden
from django.http import HttpResponseServerError
-from django.conf import settings
from django.utils import simplejson
-from django.core.serializers import json
def permission(perm):
def _dec(view_func):
- def _view(request, *args, **kwargs):
+ def _view(request, * args, ** kwargs):
if request.user.has_perm(perm) and request.user.is_authenticated():
- return view_func(request, *args, **kwargs)
+ return view_func(request, * args, ** kwargs)
else:
return HttpResponseForbidden()
@@ -25,17 +27,39 @@ def permission(perm):
class JsonResponse(HttpResponse):
def __init__(self, object):
content = simplejson.dumps(
- object, indent=2, cls=json.DjangoJSONEncoder,
- ensure_ascii=False)
+ object, indent=2, cls=json.DjangoJSONEncoder,
+ ensure_ascii=False)
super(JsonResponse, self).__init__(
- content)#, content_type='application/json')
- self['Cache-Control'] = 'no-cache, must-revalidate'
-
+ content)#, content_type='application/json') #@TODO uncomment
+ self['Cache-Control'] = 'no-cache, must-revalidate'
+@permission('pyload.can_add')
def add_package(request):
- a = {'b' : [1,2,3], 'dsfsd' : "sadd"}
- return JsonResponse(a)
+
+ name = request.POST['add_name']
+
+ if name is None or "":
+ return HttpResponseServerError()
+
+ links = request.POST['add_links'].split("\n")
+
+ try:
+ f = request.FILES['add_file']
+ fpath = join(settings.DL_ROOT, f.name)
+ destination = open(fpath, 'wb')
+ for chunk in f.chunks():
+ destination.write(chunk)
+ destination.close()
+ links.insert(0, fpath)
+ except:
+ pass
+
+ links = filter(lambda x: x is not "", links)
+
+ settings.PYLOAD.add_package(name, links)
+
+ return JsonResponse("success")
@permission('pyload.can_see_dl')
@@ -96,12 +120,12 @@ def packages(request):
return HttpResponseServerError()
@permission('pyload.can_see_dl')
-def package(request,id):
+def package(request, id):
try:
data = settings.PYLOAD.get_package_data(int(id))
data['links'] = []
for file in settings.PYLOAD.get_package_files(data['id']):
- data['links'].append(settings.PYLOAD.get_file_info(file))
+ data['links'].append(settings.PYLOAD.get_file_info(file))
return JsonResponse(data)
@@ -109,7 +133,7 @@ def package(request,id):
return HttpResponseServerError()
@permission('pyload.can_see_dl')
-def link(request,id):
+def link(request, id):
try:
data = settings.PYLOAD.get_file_info(int(id))
return JsonResponse(data)
diff --git a/module/web/manage.py b/module/web/manage.py
index 6a00ab565..34b964ffc 100755
--- a/module/web/manage.py
+++ b/module/web/manage.py
@@ -1,20 +1,13 @@
#!/usr/bin/env python
-from __future__ import with_statement
-import os
+# -*- coding: utf-8 -*-
+from django.core.management import execute_manager
-pid = os.fork()
-if pid:
- with open("webserver.pid", "w") as f:
- f.write(str(pid))
-else:
- from django.core.management import execute_manager
+try:
+ import settings # Assumed to be in the same directory.
+except ImportError:
+ import sys
+ sys.stderr.write("Error: Can't find the file 'settings.py' in the directory containing %r. It appears you've customized things.\nYou'll have to run django-admin.py, passing it your settings module.\n(If the file settings.py does indeed exist, it's causing an ImportError somehow.)\n" % __file__)
+ sys.exit(1)
- try:
- import settings # Assumed to be in the same directory.
- except ImportError:
- import sys
- sys.stderr.write("Error: Can't find the file 'settings.py' in the directory containing %r. It appears you've customized things.\nYou'll have to run django-admin.py, passing it your settings module.\n(If the file settings.py does indeed exist, it's causing an ImportError somehow.)\n" % __file__)
- sys.exit(1)
-
- if __name__ == "__main__":
- execute_manager(settings)
+if __name__ == "__main__":
+ execute_manager(settings) \ No newline at end of file
diff --git a/module/web/media/default/js/jquery.form.js b/module/web/media/default/js/jquery.form.js
new file mode 100644
index 000000000..dde394270
--- /dev/null
+++ b/module/web/media/default/js/jquery.form.js
@@ -0,0 +1,660 @@
+/*
+ * jQuery Form Plugin
+ * version: 2.36 (07-NOV-2009)
+ * @requires jQuery v1.2.6 or later
+ *
+ * Examples and documentation at: http://malsup.com/jquery/form/
+ * Dual licensed under the MIT and GPL licenses:
+ * http://www.opensource.org/licenses/mit-license.php
+ * http://www.gnu.org/licenses/gpl.html
+ */
+;(function($) {
+
+/*
+ Usage Note:
+ -----------
+ Do not use both ajaxSubmit and ajaxForm on the same form. These
+ functions are intended to be exclusive. Use ajaxSubmit if you want
+ to bind your own submit handler to the form. For example,
+
+ $(document).ready(function() {
+ $('#myForm').bind('submit', function() {
+ $(this).ajaxSubmit({
+ target: '#output'
+ });
+ return false; // <-- important!
+ });
+ });
+
+ Use ajaxForm when you want the plugin to manage all the event binding
+ for you. For example,
+
+ $(document).ready(function() {
+ $('#myForm').ajaxForm({
+ target: '#output'
+ });
+ });
+
+ When using ajaxForm, the ajaxSubmit function will be invoked for you
+ at the appropriate time.
+*/
+
+/**
+ * ajaxSubmit() provides a mechanism for immediately submitting
+ * an HTML form using AJAX.
+ */
+$.fn.ajaxSubmit = function(options) {
+ // fast fail if nothing selected (http://dev.jquery.com/ticket/2752)
+ if (!this.length) {
+ log('ajaxSubmit: skipping submit process - no element selected');
+ return this;
+ }
+
+ if (typeof options == 'function')
+ options = { success: options };
+
+ var url = $.trim(this.attr('action'));
+ if (url) {
+ // clean url (don't include hash vaue)
+ url = (url.match(/^([^#]+)/)||[])[1];
+ }
+ url = url || window.location.href || '';
+
+ options = $.extend({
+ url: url,
+ type: this.attr('method') || 'GET',
+ iframeSrc: /^https/i.test(window.location.href || '') ? 'javascript:false' : 'about:blank'
+ }, options || {});
+
+ // hook for manipulating the form data before it is extracted;
+ // convenient for use with rich editors like tinyMCE or FCKEditor
+ var veto = {};
+ this.trigger('form-pre-serialize', [this, options, veto]);
+ if (veto.veto) {
+ log('ajaxSubmit: submit vetoed via form-pre-serialize trigger');
+ return this;
+ }
+
+ // provide opportunity to alter form data before it is serialized
+ if (options.beforeSerialize && options.beforeSerialize(this, options) === false) {
+ log('ajaxSubmit: submit aborted via beforeSerialize callback');
+ return this;
+ }
+
+ var a = this.formToArray(options.semantic);
+ if (options.data) {
+ options.extraData = options.data;
+ for (var n in options.data) {
+ if(options.data[n] instanceof Array) {
+ for (var k in options.data[n])
+ a.push( { name: n, value: options.data[n][k] } );
+ }
+ else
+ a.push( { name: n, value: options.data[n] } );
+ }
+ }
+
+ // give pre-submit callback an opportunity to abort the submit
+ if (options.beforeSubmit && options.beforeSubmit(a, this, options) === false) {
+ log('ajaxSubmit: submit aborted via beforeSubmit callback');
+ return this;
+ }
+
+ // fire vetoable 'validate' event
+ this.trigger('form-submit-validate', [a, this, options, veto]);
+ if (veto.veto) {
+ log('ajaxSubmit: submit vetoed via form-submit-validate trigger');
+ return this;
+ }
+
+ var q = $.param(a);
+
+ if (options.type.toUpperCase() == 'GET') {
+ options.url += (options.url.indexOf('?') >= 0 ? '&' : '?') + q;
+ options.data = null; // data is null for 'get'
+ }
+ else
+ options.data = q; // data is the query string for 'post'
+
+ var $form = this, callbacks = [];
+ if (options.resetForm) callbacks.push(function() { $form.resetForm(); });
+ if (options.clearForm) callbacks.push(function() { $form.clearForm(); });
+
+ // perform a load on the target only if dataType is not provided
+ if (!options.dataType && options.target) {
+ var oldSuccess = options.success || function(){};
+ callbacks.push(function(data) {
+ $(options.target).html(data).each(oldSuccess, arguments);
+ });
+ }
+ else if (options.success)
+ callbacks.push(options.success);
+
+ options.success = function(data, status) {
+ for (var i=0, max=callbacks.length; i < max; i++)
+ callbacks[i].apply(options, [data, status, $form]);
+ };
+
+ // are there files to upload?
+ var files = $('input:file', this).fieldValue();
+ var found = false;
+ for (var j=0; j < files.length; j++)
+ if (files[j])
+ found = true;
+
+ var multipart = false;
+// var mp = 'multipart/form-data';
+// multipart = ($form.attr('enctype') == mp || $form.attr('encoding') == mp);
+
+ // options.iframe allows user to force iframe mode
+ // 06-NOV-09: now defaulting to iframe mode if file input is detected
+ if ((files.length && options.iframe !== false) || options.iframe || found || multipart) {
+ // hack to fix Safari hang (thanks to Tim Molendijk for this)
+ // see: http://groups.google.com/group/jquery-dev/browse_thread/thread/36395b7ab510dd5d
+ if (options.closeKeepAlive)
+ $.get(options.closeKeepAlive, fileUpload);
+ else
+ fileUpload();
+ }
+ else
+ $.ajax(options);
+
+ // fire 'notify' event
+ this.trigger('form-submit-notify', [this, options]);
+ return this;
+
+
+ // private function for handling file uploads (hat tip to YAHOO!)
+ function fileUpload() {
+ var form = $form[0];
+
+ if ($(':input[name=submit]', form).length) {
+ alert('Error: Form elements must not be named "submit".');
+ return;
+ }
+
+ var opts = $.extend({}, $.ajaxSettings, options);
+ var s = $.extend(true, {}, $.extend(true, {}, $.ajaxSettings), opts);
+
+ var id = 'jqFormIO' + (new Date().getTime());
+ var $io = $('<iframe id="' + id + '" name="' + id + '" src="'+ opts.iframeSrc +'" />');
+ var io = $io[0];
+
+ $io.css({ position: 'absolute', top: '-1000px', left: '-1000px' });
+
+ var xhr = { // mock object
+ aborted: 0,
+ responseText: null,
+ responseXML: null,
+ status: 0,
+ statusText: 'n/a',
+ getAllResponseHeaders: function() {},
+ getResponseHeader: function() {},
+ setRequestHeader: function() {},
+ abort: function() {
+ this.aborted = 1;
+ $io.attr('src', opts.iframeSrc); // abort op in progress
+ }
+ };
+
+ var g = opts.global;
+ // trigger ajax global events so that activity/block indicators work like normal
+ if (g && ! $.active++) $.event.trigger("ajaxStart");
+ if (g) $.event.trigger("ajaxSend", [xhr, opts]);
+
+ if (s.beforeSend && s.beforeSend(xhr, s) === false) {
+ s.global && $.active--;
+ return;
+ }
+ if (xhr.aborted)
+ return;
+
+ var cbInvoked = 0;
+ var timedOut = 0;
+
+ // add submitting element to data if we know it
+ var sub = form.clk;
+ if (sub) {
+ var n = sub.name;
+ if (n && !sub.disabled) {
+ options.extraData = options.extraData || {};
+ options.extraData[n] = sub.value;
+ if (sub.type == "image") {
+ options.extraData[name+'.x'] = form.clk_x;
+ options.extraData[name+'.y'] = form.clk_y;
+ }
+ }
+ }
+
+ // take a breath so that pending repaints get some cpu time before the upload starts
+ setTimeout(function() {
+ // make sure form attrs are set
+ var t = $form.attr('target'), a = $form.attr('action');
+
+ // update form attrs in IE friendly way
+ form.setAttribute('target',id);
+ if (form.getAttribute('method') != 'POST')
+ form.setAttribute('method', 'POST');
+ if (form.getAttribute('action') != opts.url)
+ form.setAttribute('action', opts.url);
+
+ // ie borks in some cases when setting encoding
+ if (! options.skipEncodingOverride) {
+ $form.attr({
+ encoding: 'multipart/form-data',
+ enctype: 'multipart/form-data'
+ });
+ }
+
+ // support timout
+ if (opts.timeout)
+ setTimeout(function() { timedOut = true; cb(); }, opts.timeout);
+
+ // add "extra" data to form if provided in options
+ var extraInputs = [];
+ try {
+ if (options.extraData)
+ for (var n in options.extraData)
+ extraInputs.push(
+ $('<input type="hidden" name="'+n+'" value="'+options.extraData[n]+'" />')
+ .appendTo(form)[0]);
+
+ // add iframe to doc and submit the form
+ $io.appendTo('body');
+ io.attachEvent ? io.attachEvent('onload', cb) : io.addEventListener('load', cb, false);
+ form.submit();
+ }
+ finally {
+ // reset attrs and remove "extra" input elements
+ form.setAttribute('action',a);
+ t ? form.setAttribute('target', t) : $form.removeAttr('target');
+ $(extraInputs).remove();
+ }
+ }, 10);
+
+ var domCheckCount = 50;
+
+ function cb() {
+ if (cbInvoked++) return;
+
+ io.detachEvent ? io.detachEvent('onload', cb) : io.removeEventListener('load', cb, false);
+
+ var ok = true;
+ try {
+ if (timedOut) throw 'timeout';
+ // extract the server response from the iframe
+ var data, doc;
+
+ doc = io.contentWindow ? io.contentWindow.document : io.contentDocument ? io.contentDocument : io.document;
+
+ var isXml = opts.dataType == 'xml' || doc.XMLDocument || $.isXMLDoc(doc);
+ log('isXml='+isXml);
+ if (!isXml && (doc.body == null || doc.body.innerHTML == '')) {
+ if (--domCheckCount) {
+ // in some browsers (Opera) the iframe DOM is not always traversable when
+ // the onload callback fires, so we loop a bit to accommodate
+ cbInvoked = 0;
+ setTimeout(cb, 100);
+ return;
+ }
+ log('Could not access iframe DOM after 50 tries.');
+ return;
+ }
+
+ xhr.responseText = doc.body ? doc.body.innerHTML : null;
+ xhr.responseXML = doc.XMLDocument ? doc.XMLDocument : doc;
+ xhr.getResponseHeader = function(header){
+ var headers = {'content-type': opts.dataType};
+ return headers[header];
+ };
+
+ if (opts.dataType == 'json' || opts.dataType == 'script') {
+ // see if user embedded response in textarea
+ var ta = doc.getElementsByTagName('textarea')[0];
+ if (ta)
+ xhr.responseText = ta.value;
+ else {
+ // account for browsers injecting pre around json response
+ var pre = doc.getElementsByTagName('pre')[0];
+ if (pre)
+ xhr.responseText = pre.innerHTML;
+ }
+ }
+ else if (opts.dataType == 'xml' && !xhr.responseXML && xhr.responseText != null) {
+ xhr.responseXML = toXml(xhr.responseText);
+ }
+ data = $.httpData(xhr, opts.dataType);
+ }
+ catch(e){
+ ok = false;
+ $.handleError(opts, xhr, 'error', e);
+ }
+
+ // ordering of these callbacks/triggers is odd, but that's how $.ajax does it
+ if (ok) {
+ opts.success(data, 'success');
+ if (g) $.event.trigger("ajaxSuccess", [xhr, opts]);
+ }
+ if (g) $.event.trigger("ajaxComplete", [xhr, opts]);
+ if (g && ! --$.active) $.event.trigger("ajaxStop");
+ if (opts.complete) opts.complete(xhr, ok ? 'success' : 'error');
+
+ // clean up
+ setTimeout(function() {
+ $io.remove();
+ xhr.responseXML = null;
+ }, 100);
+ };
+
+ function toXml(s, doc) {
+ if (window.ActiveXObject) {
+ doc = new ActiveXObject('Microsoft.XMLDOM');
+ doc.async = 'false';
+ doc.loadXML(s);
+ }
+ else
+ doc = (new DOMParser()).parseFromString(s, 'text/xml');
+ return (doc && doc.documentElement && doc.documentElement.tagName != 'parsererror') ? doc : null;
+ };
+ };
+};
+
+/**
+ * ajaxForm() provides a mechanism for fully automating form submission.
+ *
+ * The advantages of using this method instead of ajaxSubmit() are:
+ *
+ * 1: This method will include coordinates for <input type="image" /> elements (if the element
+ * is used to submit the form).
+ * 2. This method will include the submit element's name/value data (for the element that was
+ * used to submit the form).
+ * 3. This method binds the submit() method to the form for you.
+ *
+ * The options argument for ajaxForm works exactly as it does for ajaxSubmit. ajaxForm merely
+ * passes the options argument along after properly binding events for submit elements and
+ * the form itself.
+ */
+$.fn.ajaxForm = function(options) {
+ return this.ajaxFormUnbind().bind('submit.form-plugin', function() {
+ $(this).ajaxSubmit(options);
+ return false;
+ }).bind('click.form-plugin', function(e) {
+ var target = e.target;
+ var $el = $(target);
+ if (!($el.is(":submit,input:image"))) {
+ // is this a child element of the submit el? (ex: a span within a button)
+ var t = $el.closest(':submit');
+ if (t.length == 0)
+ return;
+ target = t[0];
+ }
+ var form = this;
+ form.clk = target;
+ if (target.type == 'image') {
+ if (e.offsetX != undefined) {
+ form.clk_x = e.offsetX;
+ form.clk_y = e.offsetY;
+ } else if (typeof $.fn.offset == 'function') { // try to use dimensions plugin
+ var offset = $el.offset();
+ form.clk_x = e.pageX - offset.left;
+ form.clk_y = e.pageY - offset.top;
+ } else {
+ form.clk_x = e.pageX - target.offsetLeft;
+ form.clk_y = e.pageY - target.offsetTop;
+ }
+ }
+ // clear form vars
+ setTimeout(function() { form.clk = form.clk_x = form.clk_y = null; }, 100);
+ });
+};
+
+// ajaxFormUnbind unbinds the event handlers that were bound by ajaxForm
+$.fn.ajaxFormUnbind = function() {
+ return this.unbind('submit.form-plugin click.form-plugin');
+};
+
+/**
+ * formToArray() gathers form element data into an array of objects that can
+ * be passed to any of the following ajax functions: $.get, $.post, or load.
+ * Each object in the array has both a 'name' and 'value' property. An example of
+ * an array for a simple login form might be:
+ *
+ * [ { name: 'username', value: 'jresig' }, { name: 'password', value: 'secret' } ]
+ *
+ * It is this array that is passed to pre-submit callback functions provided to the
+ * ajaxSubmit() and ajaxForm() methods.
+ */
+$.fn.formToArray = function(semantic) {
+ var a = [];
+ if (this.length == 0) return a;
+
+ var form = this[0];
+ var els = semantic ? form.getElementsByTagName('*') : form.elements;
+ if (!els) return a;
+ for(var i=0, max=els.length; i < max; i++) {
+ var el = els[i];
+ var n = el.name;
+ if (!n) continue;
+
+ if (semantic && form.clk && el.type == "image") {
+ // handle image inputs on the fly when semantic == true
+ if(!el.disabled && form.clk == el) {
+ a.push({name: n, value: $(el).val()});
+ a.push({name: n+'.x', value: form.clk_x}, {name: n+'.y', value: form.clk_y});
+ }
+ continue;
+ }
+
+ var v = $.fieldValue(el, true);
+ if (v && v.constructor == Array) {
+ for(var j=0, jmax=v.length; j < jmax; j++)
+ a.push({name: n, value: v[j]});
+ }
+ else if (v !== null && typeof v != 'undefined')
+ a.push({name: n, value: v});
+ }
+
+ if (!semantic && form.clk) {
+ // input type=='image' are not found in elements array! handle it here
+ var $input = $(form.clk), input = $input[0], n = input.name;
+ if (n && !input.disabled && input.type == 'image') {
+ a.push({name: n, value: $input.val()});
+ a.push({name: n+'.x', value: form.clk_x}, {name: n+'.y', value: form.clk_y});
+ }
+ }
+ return a;
+};
+
+/**
+ * Serializes form data into a 'submittable' string. This method will return a string
+ * in the format: name1=value1&amp;name2=value2
+ */
+$.fn.formSerialize = function(semantic) {
+ //hand off to jQuery.param for proper encoding
+ return $.param(this.formToArray(semantic));
+};
+
+/**
+ * Serializes all field elements in the jQuery object into a query string.
+ * This method will return a string in the format: name1=value1&amp;name2=value2
+ */
+$.fn.fieldSerialize = function(successful) {
+ var a = [];
+ this.each(function() {
+ var n = this.name;
+ if (!n) return;
+ var v = $.fieldValue(this, successful);
+ if (v && v.constructor == Array) {
+ for (var i=0,max=v.length; i < max; i++)
+ a.push({name: n, value: v[i]});
+ }
+ else if (v !== null && typeof v != 'undefined')
+ a.push({name: this.name, value: v});
+ });
+ //hand off to jQuery.param for proper encoding
+ return $.param(a);
+};
+
+/**
+ * Returns the value(s) of the element in the matched set. For example, consider the following form:
+ *
+ * <form><fieldset>
+ * <input name="A" type="text" />
+ * <input name="A" type="text" />
+ * <input name="B" type="checkbox" value="B1" />
+ * <input name="B" type="checkbox" value="B2"/>
+ * <input name="C" type="radio" value="C1" />
+ * <input name="C" type="radio" value="C2" />
+ * </fieldset></form>
+ *
+ * var v = $(':text').fieldValue();
+ * // if no values are entered into the text inputs
+ * v == ['','']
+ * // if values entered into the text inputs are 'foo' and 'bar'
+ * v == ['foo','bar']
+ *
+ * var v = $(':checkbox').fieldValue();
+ * // if neither checkbox is checked
+ * v === undefined
+ * // if both checkboxes are checked
+ * v == ['B1', 'B2']
+ *
+ * var v = $(':radio').fieldValue();
+ * // if neither radio is checked
+ * v === undefined
+ * // if first radio is checked
+ * v == ['C1']
+ *
+ * The successful argument controls whether or not the field element must be 'successful'
+ * (per http://www.w3.org/TR/html4/interact/forms.html#successful-controls).
+ * The default value of the successful argument is true. If this value is false the value(s)
+ * for each element is returned.
+ *
+ * Note: This method *always* returns an array. If no valid value can be determined the
+ * array will be empty, otherwise it will contain one or more values.
+ */
+$.fn.fieldValue = function(successful) {
+ for (var val=[], i=0, max=this.length; i < max; i++) {
+ var el = this[i];
+ var v = $.fieldValue(el, successful);
+ if (v === null || typeof v == 'undefined' || (v.constructor == Array && !v.length))
+ continue;
+ v.constructor == Array ? $.merge(val, v) : val.push(v);
+ }
+ return val;
+};
+
+/**
+ * Returns the value of the field element.
+ */
+$.fieldValue = function(el, successful) {
+ var n = el.name, t = el.type, tag = el.tagName.toLowerCase();
+ if (typeof successful == 'undefined') successful = true;
+
+ if (successful && (!n || el.disabled || t == 'reset' || t == 'button' ||
+ (t == 'checkbox' || t == 'radio') && !el.checked ||
+ (t == 'submit' || t == 'image') && el.form && el.form.clk != el ||
+ tag == 'select' && el.selectedIndex == -1))
+ return null;
+
+ if (tag == 'select') {
+ var index = el.selectedIndex;
+ if (index < 0) return null;
+ var a = [], ops = el.options;
+ var one = (t == 'select-one');
+ var max = (one ? index+1 : ops.length);
+ for(var i=(one ? index : 0); i < max; i++) {
+ var op = ops[i];
+ if (op.selected) {
+ var v = op.value;
+ if (!v) // extra pain for IE...
+ v = (op.attributes && op.attributes['value'] && !(op.attributes['value'].specified)) ? op.text : op.value;
+ if (one) return v;
+ a.push(v);
+ }
+ }
+ return a;
+ }
+ return el.value;
+};
+
+/**
+ * Clears the form data. Takes the following actions on the form's input fields:
+ * - input text fields will have their 'value' property set to the empty string
+ * - select elements will have their 'selectedIndex' property set to -1
+ * - checkbox and radio inputs will have their 'checked' property set to false
+ * - inputs of type submit, button, reset, and hidden will *not* be effected
+ * - button elements will *not* be effected
+ */
+$.fn.clearForm = function() {
+ return this.each(function() {
+ $('input,select,textarea', this).clearFields();
+ });
+};
+
+/**
+ * Clears the selected form elements.
+ */
+$.fn.clearFields = $.fn.clearInputs = function() {
+ return this.each(function() {
+ var t = this.type, tag = this.tagName.toLowerCase();
+ if (t == 'text' || t == 'password' || tag == 'textarea')
+ this.value = '';
+ else if (t == 'checkbox' || t == 'radio')
+ this.checked = false;
+ else if (tag == 'select')
+ this.selectedIndex = -1;
+ });
+};
+
+/**
+ * Resets the form data. Causes all form elements to be reset to their original value.
+ */
+$.fn.resetForm = function() {
+ return this.each(function() {
+ // guard against an input with the name of 'reset'
+ // note that IE reports the reset function as an 'object'
+ if (typeof this.reset == 'function' || (typeof this.reset == 'object' && !this.reset.nodeType))
+ this.reset();
+ });
+};
+
+/**
+ * Enables or disables any matching elements.
+ */
+$.fn.enable = function(b) {
+ if (b == undefined) b = true;
+ return this.each(function() {
+ this.disabled = !b;
+ });
+};
+
+/**
+ * Checks/unchecks any matching checkboxes or radio buttons and
+ * selects/deselects and matching option elements.
+ */
+$.fn.selected = function(select) {
+ if (select == undefined) select = true;
+ return this.each(function() {
+ var t = this.type;
+ if (t == 'checkbox' || t == 'radio')
+ this.checked = select;
+ else if (this.tagName.toLowerCase() == 'option') {
+ var $sel = $(this).parent('select');
+ if (select && $sel[0] && $sel[0].type == 'select-one') {
+ // deselect all other options
+ $sel.find('option').selected(false);
+ }
+ this.selected = select;
+ }
+ });
+};
+
+// helper fn for console logging
+// set $.fn.ajaxSubmit.debug to true to enable debug logging
+function log() {
+ if ($.fn.ajaxSubmit.debug && window.console && window.console.log)
+ window.console.log('[jquery.form] ' + Array.prototype.join.call(arguments,''));
+};
+
+})(jQuery);
diff --git a/module/web/pyload/views.py b/module/web/pyload/views.py
index e38a0abf5..35d777020 100644
--- a/module/web/pyload/views.py
+++ b/module/web/pyload/views.py
@@ -2,27 +2,28 @@
# Create your views here.
import mimetypes
+from os import listdir
+from os import stat
+from os.path import isdir
+from os.path import isfile
+from os.path import join
+
+from django.conf import settings
+from django.contrib.auth.decorators import login_required
from django.http import HttpResponse
from django.http import HttpResponseNotFound
-from django.conf import settings
from django.shortcuts import render_to_response
from django.template import RequestContext
-from django.contrib.auth.decorators import login_required
-from os.path import join
-from os.path import isdir
-from os.path import isfile
-from os import listdir
-from os import stat
def check_server(function):
def _dec(view_func):
- def _view(request, *args, **kwargs):
+ def _view(request, * args, ** kwargs):
try:
version = settings.PYLOAD.get_server_version()
except Exception, e:
- return base(request, messages=['Can\'t connect to pyLoad. Please check your configuration and make sure pyLoad is running.',str(e)])
- return view_func(request, *args, **kwargs)
+ return base(request, messages=['Can\'t connect to pyLoad. Please check your configuration and make sure pyLoad is running.', str(e)])
+ return view_func(request, * args, ** kwargs)
_view.__name__ = view_func.__name__
_view.__dict__ = view_func.__dict__
@@ -38,9 +39,9 @@ def check_server(function):
def permission(perm):
def _dec(view_func):
- def _view(request, *args, **kwargs):
+ def _view(request, * args, ** kwargs):
if request.user.has_perm(perm):
- return view_func(request, *args, **kwargs)
+ return view_func(request, * args, ** kwargs)
else:
return base(request, messages=['You don\'t have permission to view this page.'])
@@ -59,20 +60,20 @@ def status_proc(request):
def base(request, messages):
- return render_to_response(join(settings.TEMPLATE,'base.html'), {'messages': messages},RequestContext(request))
+ return render_to_response(join(settings.TEMPLATE, 'base.html'), {'messages': messages}, RequestContext(request))
@login_required
@permission('pyload.can_see_dl')
@check_server
def home(request):
- return render_to_response(join(settings.TEMPLATE,'home.html'), RequestContext(request,{'content': settings.PYLOAD.status_downloads()},[status_proc]))
+ return render_to_response(join(settings.TEMPLATE, 'home.html'), RequestContext(request, {'content': settings.PYLOAD.status_downloads()}, [status_proc]))
@login_required
@permission('pyload.can_see_dl')
@check_server
def queue(request):
- return render_to_response(join(settings.TEMPLATE,'queue.html'), RequestContext(request,{},[status_proc]))
+ return render_to_response(join(settings.TEMPLATE, 'queue.html'), RequestContext(request, {}, [status_proc]))
@login_required
@@ -89,8 +90,8 @@ def downloads(request):
for item in listdir(settings.DL_ROOT):
if isdir(join(settings.DL_ROOT, item)):
folder = {
- 'name' : item,
- 'files' : []
+ 'name': item,
+ 'files': []
}
for file in listdir(join(settings.DL_ROOT, item)):
if isfile(join(settings.DL_ROOT, item, file)):
@@ -101,15 +102,15 @@ def downloads(request):
data['files'].append(item)
- return render_to_response(join(settings.TEMPLATE,'downloads.html'), RequestContext(request,{'files': data},[status_proc]))
+ return render_to_response(join(settings.TEMPLATE, 'downloads.html'), RequestContext(request, {'files': data}, [status_proc]))
@login_required
@permission('pyload.user.can_download')
@check_server
-def download(request,path):
+def download(request, path):
path = path.split("/")
- dir = join(settings.DL_ROOT, path[1].replace('..',''))
+ dir = join(settings.DL_ROOT, path[1].replace('..', ''))
if isdir(dir) or isfile(dir):
if isdir(dir): filepath = join(dir, path[2])
elif isfile(dir): filepath = dir
@@ -125,7 +126,7 @@ def download(request,path):
response['Content-Length'] = str(stat(filepath).st_size)
if encoding is not None:
- response['Content-Encoding'] = encoding
+ response['Content-Encoding'] = encoding
response.write(file(filepath, "rb").read())
return response
@@ -143,7 +144,7 @@ def logs(request, page=0):
log = file(join(settings.LOG_ROOT, "log.txt")).readlines()
data = []
page = int(page)
- for i in range(page, page+20):
- data.append({'line': i+1 , 'content' :log[i]})
+ for i in range(page, page + 20):
+ data.append({'line': i + 1, 'content':log[i]})
- return render_to_response(join(settings.TEMPLATE,'logs.html'), RequestContext(request,{'log': data, 'next': str(page+20) , 'prev': 0 if page-20 < 0 else page-20},[status_proc])) \ No newline at end of file
+ return render_to_response(join(settings.TEMPLATE, 'logs.html'), RequestContext(request, {'log': data, 'next': str(page + 20), 'prev': 0 if page-20 < 0 else page-20}, [status_proc])) \ No newline at end of file
diff --git a/module/web/run_unix.py b/module/web/run_unix.py
new file mode 100755
index 000000000..09c67b282
--- /dev/null
+++ b/module/web/run_unix.py
@@ -0,0 +1,21 @@
+#!/usr/bin/env python
+# -*- coding: utf-8 -*-
+from __future__ import with_statement
+import os
+
+pid = os.fork()
+if pid:
+ with open("webserver.pid", "w") as f:
+ f.write(str(pid))
+else:
+ from django.core.management import execute_manager
+
+ try:
+ import settings # Assumed to be in the same directory.
+ except ImportError:
+ import sys
+ sys.stderr.write("Error: Can't find the file 'settings.py' in the directory containing %r. It appears you've customized things.\nYou'll have to run django-admin.py, passing it your settings module.\n(If the file settings.py does indeed exist, it's causing an ImportError somehow.)\n" % __file__)
+ sys.exit(1)
+
+ if __name__ == "__main__":
+ execute_manager(settings) \ No newline at end of file
diff --git a/module/web/settings.py b/module/web/settings.py
index 3b242164c..dff1dc29d 100644
--- a/module/web/settings.py
+++ b/module/web/settings.py
@@ -132,4 +132,4 @@ INSTALLED_APPS = (
AUTH_PROFILE_MODULE = 'pyload.UserProfile'
-LOGIN_URL = '/login'
+LOGIN_URL = '/login' \ No newline at end of file
diff --git a/module/web/templates/default/base.html b/module/web/templates/default/base.html
index cd0b85903..7171a1f1c 100644
--- a/module/web/templates/default/base.html
+++ b/module/web/templates/default/base.html
@@ -12,13 +12,16 @@
<script src="{{ MEDIA_URL }}js/sprintf.js"></script>
<script src="{{ MEDIA_URL }}js/funktions.js"></script>
<script src="{{ MEDIA_URL }}js/jquery.progressbar.js"></script>
+<script src="{{ MEDIA_URL }}js/jquery.form.js"></script>
<title>{% block title %}pyLoad Webinterface{% endblock %}</title>
<script type="text/javascript">
$(document).ready(function(){
$.getJSON('/json/status', LoadJsonToContent );
- $.getJSON('/json/links', LinksToContent );
+ $('#add_form').ajaxForm(function() {
+ AddBox();
+ }); 
});
@@ -58,20 +61,6 @@ function AddBox()
}
}
-function AddSubmit()
-{
- $("#add_form").submit();
- /*
- $.post("/json/add_package", { links: $("#add_links").text() } );
- return false;
- if( $("#add_cf").val() != "" )
- {
- //$("#add_form").submit();
- }
- */
- AddBox();
-
-}
</script>
{% block head %}
diff --git a/module/web/templates/default/home.html b/module/web/templates/default/home.html
index 49633f94a..96f3015d9 100644
--- a/module/web/templates/default/home.html
+++ b/module/web/templates/default/home.html
@@ -9,6 +9,9 @@
$("#aktiv_percent").text(parseInt($("#aktiv_percent").text)+1)
setTimeout( UpdateLinks( SetInver, index+1 ), SetInver[index]*1000);
}*/
+$(document).ready(function(){
+ $.getJSON('/json/links', LinksToContent );
+});
function LinksToContent(data)
{
diff --git a/module/web/templates/default/window.html b/module/web/templates/default/window.html
index ec4ca496a..fa49565d3 100644
--- a/module/web/templates/default/window.html
+++ b/module/web/templates/default/window.html
@@ -2,10 +2,11 @@
<div id="add_box" style="left:50%; top:200px; margin-left: -450px; width: 900px; position: absolute; background: #FFF; padding: 10px 10px 10px 10px; display:none;">
<div style="width: 900px; text-align: right;"><b onclick="AddBox();">[Close]</b></div>
<h1>Add</h1>
- <form id="add_form" action="" method="post" onsubmit="return AddSubmit();">
+ <form id="add_form" action="json/add_package" method="post">
+ Packagename<input name="add_name" type="text" size="20" />
<textarea rows="5" style="width: 890px;" name="add_links" id="add_links"></textarea>
<br />
- <input type="file" name="add_cf" id="add_cf" />
- <input type="submit" value="Add Links" />
+ <input type="file" name="add_file" id="add_file" />
+ <input id="add_submit" type="submit" value="Add Links"/>
</form>
</div>
diff --git a/pyLoadCli.py b/pyLoadCli.py
index fd8a1f590..1ebf5d943 100755
--- a/pyLoadCli.py
+++ b/pyLoadCli.py
@@ -17,19 +17,15 @@
# along with this program; if not, see <http://www.gnu.org/licenses/>.
#
###
-import ConfigParser
-import subprocess
import os
import os.path
-from os import chdir
-from os.path import join
from os.path import abspath
from os.path import dirname
-from os import sep
-from time import sleep
+from os.path import join
import sys
-import time
import threading
+import time
+from time import sleep
import xmlrpclib
from module.XMLConfigParser import XMLConfigParser
@@ -192,7 +188,7 @@ class pyLoadCli:
line += 1
self.println(line, "Parse the links you want to add.")
line += 1
- self.println(line, "Type "+mag("END")+" when done.")
+ self.println(line, "Type " + mag("END") + " when done.")
line += 1
self.println(line, "Links added: " + mag(str(self.links_added)))
line += 1
@@ -232,7 +228,7 @@ class pyLoadCli:
if not link['status_filename']:
self.println(line, mag(str(link['id'])) + ": " + link['url'])
else:
- self.println(line, mag(str(link['id'])) + ": %s | %s | %s" % (link['filename'],link['status_type'],link['plugin']))
+ self.println(line, mag(str(link['id'])) + ": %s | %s | %s" % (link['filename'], link['status_type'], link['plugin']))
line += 1
i += 1
@@ -429,20 +425,20 @@ if __name__ == "__main__":
for option, params in opts:
if option in ("-l", "--local"):
- xmlconfig = XMLConfigParser(join(abspath(dirname(__file__)),"module","config","core.xml"))
+ xmlconfig = XMLConfigParser(join(abspath(dirname(__file__)), "module", "config", "core.xml"))
config = xmlconfig.getConfig()
- ssl= ""
+ ssl = ""
if config['ssl']['activated'] == "True":
ssl = "s"
server_url = "http%s://%s:%s@%s:%s/" % (
- ssl,
- config['remote']['username'],
- config['remote']['password'],
- config['remote']['listenaddr'],
- config['remote']['port']
- )
+ ssl,
+ config['remote']['username'],
+ config['remote']['password'],
+ config['remote']['listenaddr'],
+ config['remote']['port']
+ )
if len(extraparams) == 1:
server_url = sys.argv[1]
else:
diff --git a/pyLoadCore.py b/pyLoadCore.py
index 16c272d5e..5ae81294d 100755
--- a/pyLoadCore.py
+++ b/pyLoadCore.py
@@ -28,49 +28,43 @@ from glob import glob
from imp import find_module
import logging
import logging.handlers
-from os import listdir
+from os import execv
from os import makedirs
-from os import sep
+from os import sep
from os.path import basename
-from os.path import abspath
from os.path import dirname
from os.path import exists
from os.path import join
-from os import execv
-from sys import stdin
from re import sub
import subprocess
from sys import argv
+from sys import executable
from sys import exit
from sys import path
from sys import stdout
-from sys import executable
+from tempfile import NamedTemporaryFile
import thread
import time
from time import sleep
-from shutil import copyfile
-from tempfile import NamedTemporaryFile
+from xmlrpclib import Binary
-from module.network.Request import Request
-import module.remote.SecureXMLRPCServer as Server
+from module.CaptchaManager import CaptchaManager
+from module.HookManager import HookManager
from module.XMLConfigParser import XMLConfigParser
-
from module.file_list import File_List
+from module.network.Request import Request
+import module.remote.SecureXMLRPCServer as Server
from module.thread_list import Thread_List
from module.web.ServerThread import WebServer
-from module.CaptchaManager import CaptchaManager
-from module.HookManager import HookManager
-
-from xmlrpclib import Binary
class Core(object):
""" pyLoad Core """
def __init__(self):
if len(argv) > 1:
if argv[1] == "-v" or argv[1] == "--version":
- print "pyLoad", CURRENT_VERSION
- else:
- print "Unknown Command"
+ print "pyLoad", CURRENT_VERSION
+ else:
+ print "Unknown Command"
exit()
def toggle_pause(self):
@@ -90,7 +84,7 @@ class Core(object):
self.plugin_folder = join("module", "plugins")
- self.xmlconfig = XMLConfigParser(join(self.path,"module","config","core.xml"))
+ self.xmlconfig = XMLConfigParser(join(self.path, "module", "config", "core.xml"))
self.config = self.xmlconfig.getConfig()
self.do_kill = False
@@ -136,7 +130,7 @@ class Core(object):
self.last_update_check = 0
self.update_check_interval = 1800
self.update_available = self.check_update()
- self.logger.info(_("Downloadtime: %s") % self.server_methods.is_time_download())
+ self.logger.info(_("Downloadtime: %s") % self.server_methods.is_time_download())
self.init_server()
self.init_webserver()
@@ -265,7 +259,7 @@ class Core(object):
exit()
def isGUIConnected(self):
- return self.lastGuiConnected+10 > time.time()
+ return self.lastGuiConnected + 10 > time.time()
def restart(self):
self.shutdown()
@@ -512,7 +506,7 @@ class ServerMethods():
self.core.file_list.packager.resetFileStatus(fileid)
def upload_container(self, filename, type, content):
- th = NamedTemporaryFile(mode="w", suffix="."+type, delete=False)
+ th = NamedTemporaryFile(mode="w", suffix="." + type, delete=False)
th.write(content)
path = th.name
th.close()