#!/usr/bin/python
+import functools
import logging
+import tornado.ioloop
import tornado.web
from .. import Backend
from . import handlers
+from . import queue
class Application(tornado.web.Application):
def __init__(self, **settings):
# Packages
(r"/packages/(.*)", handlers.PackagesGetHandler),
+ # Queue
+ (r"/queue", queue.QueueHandler),
+
# Uploads
(r"/upload", handlers.UploadHandler),
], **settings)
# Launch backend
self.backend = Backend()
+ # Launch any background jobs
+ self._run_task(queue.dispatch_jobs, 5)
+
logging.info("Successfully initialied application")
+
+ def _run_task(self, callback, t):
+ """
+ Runs the callback every t seconds in the background
+ """
+ # Pass backend to the function
+ callback = functools.partial(callback, self.backend)
+
+ # Create a periodic callback object
+ task = tornado.ioloop.PeriodicCallback(callback, t * 1000)
+
+ # Start the task
+ task.start()
--- /dev/null
+#!/usr/bin/python3
+###############################################################################
+# #
+# Pakfire - The IPFire package management system #
+# Copyright (C) 2011 Pakfire development team #
+# #
+# 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/>. #
+# #
+###############################################################################
+
+import logging
+import tornado.websocket
+
+from .handlers import BackendMixin, HTTPBasicAuthMixin
+
+log = logging.getLogger("pakfire.hub.queue")
+
+# A list of all builders that have a connection
+connections = []
+
+def dispatch_jobs(backend):
+ """
+ Will be called regularly and will dispatch any pending jobs to any
+ available builders
+ """
+ log.debug("Dispatching jobs...")
+
+ # Exit if there are no builders connected
+ if not connections:
+ log.debug(" No connections open")
+ return
+
+ # Process all connections
+ for connection in connections:
+ log.debug(" Processing connection for %s" % connection.builder)
+
+ with backend.db.transaction():
+ pass
+
+ # XXX TODO
+
+
+class QueueHandler(BackendMixin, HTTPBasicAuthMixin, tornado.websocket.WebSocketHandler):
+ """
+ Builders connect to this handler which will add them to a list of connections.
+
+ For all connections, we regularly check if we have any new build jobs, and if so,
+ we will send them the job.
+ """
+ def get_current_user(self):
+ name, password = self.get_basic_auth_credentials()
+ if name is None:
+ return
+
+ return self.backend.builders.auth(name, password)
+
+ @property
+ def builder(self):
+ return self.current_user
+
+ @tornado.web.authenticated
+ def open(self):
+ log.debug("Connection opened by %s" % self.builder)
+
+ # Add this connection to the list
+ connections.append(self)
+
+ def on_close(self):
+ log.debug("Connection to %s closed" % self.builder)
+
+ # Remove the connection
+ try:
+ connections.remove(self)
+ except IndexError:
+ pass