Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(16)

Unified Diff: chromium-jobqueue/app.py

Issue 23093011: Create tryserver appengine app. (Closed) Base URL: svn://svn.chromium.org/chrome/trunk/tools/
Patch Set: Created 7 years, 4 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View side-by-side diff with in-line comments
Download patch
« no previous file with comments | « chromium-jobqueue/LICENSE ('k') | chromium-jobqueue/app.yaml » ('j') | no next file with comments »
Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
Index: chromium-jobqueue/app.py
===================================================================
--- chromium-jobqueue/app.py (revision 0)
+++ chromium-jobqueue/app.py (revision 0)
@@ -0,0 +1,130 @@
+# Copyright (c) 2013 The Chromium Authors. All rights reserved.
+# Use of this source code is governed by a BSD-style license that can be
+# found in the LICENSE file.
+
+import datetime
+import json
+
+import webapp2
+from google.appengine.ext import ndb
+
+
+DEFAULT_NAMESPACE = 'default'
+DEFAULT_JOBS_TO_SERVE = 20
+
+
+class Job(ndb.Model):
+ """Represents a single build job description.
+
+ Attributes:
+ description: A JSON blob representing the job itself.
+ created: A timestamp for when this job was posted.
+ last_served: A timestamp for the last time this job was served, usually
+ to a polling buildbot. Default is epoch 0, so new jobs are "old".
+ taken: A boolean signalling that this job has been successfully picked
+ up by a poller and can be dropped.
+ """
+ description = ndb.JsonProperty()
+ last_served = ndb.DateTimeProperty(
+ default=datetime.datetime.utcfromtimestamp(0))
+ taken = ndb.BooleanProperty(default=False)
+
+
+class MainHandler(webapp2.RequestHandler):
+
+ def get(self):
+ self.response.write("""
+<html>
+ <body>
+ <form action="/default/push" method="post">
+ <div><textarea name="job" rows="3" cols="60"></textarea></div>
+ <div><input type="submit" value="Add Job"></div>
+ </form>
+ <form action="/default/accept" method="post">
+ <div><textarea name="job" rows="1" cols="60"></textarea></div>
+ <div><input type="submit" value="Accept Job"></div>
+ </form>
+ </body>
+</html>
+""")
+
+
+class PushHandler(webapp2.RequestHandler):
+
+ def post(self, project):
+ job = Job(description=self.request.get('job'), namespace=project)
+ job.put()
+
+
+class PullHandler(webapp2.RequestHandler):
+
+ def post(self, project):
+ # Get the jobs we'd like to serve.
+ time_threshold = datetime.datetime.utcnow() - datetime.timedelta(seconds=30)
+ query = Job.query(namespace=project)
+ query = query.filter(Job.last_served < time_threshold)
+ query = query.filter(Job.taken == False)
+ query = query.order(Job.last_served)
+ jobs = query.fetch(DEFAULT_JOBS_TO_SERVE)
+
+ # Mark them as served.
+ for job in jobs:
+ job.last_served = datetime.datetime.utcnow()
+ job.put()
+
+ # Serve them.
+ result = []
+ for job in jobs:
+ job_blob = json.loads(job.description)
+ job_blob.update({'job_key': job.key.urlsafe()})
+ result.append(job_blob)
+ self.response.headers['Content-Type'] = 'application/json'
+ self.response.write(json.dumps(result))
+
+
+class PeekHandler(webapp2.RequestHandler):
+
+ def get(self, project, job):
+ # Get the jobs we'd like to serve.
+ if job:
+ job_key = ndb.Key(urlsafe=job, namespace=project)
+ job = job_key.get()
+ jobs = [job]
+ else:
+ time_threshold = (datetime.datetime.utcnow() -
+ datetime.timedelta(seconds=30))
+ query = Job.query(namespace=project)
+ query = query.filter(Job.last_served < time_threshold)
+ query = query.filter(Job.taken == False)
+ query = query.order(Job.last_served)
+ jobs = query.fetch(DEFAULT_JOBS_TO_SERVE)
+
+ # Serve them.
+ result = []
+ for job in jobs:
+ job_blob = json.loads(job.description)
+ job_blob.update({'job_key': job.key.urlsafe()})
+ result.append(job_blob)
+ self.response.headers['Content-Type'] = 'application/json'
+ self.response.write(json.dumps(result))
+
+
+class AcceptHandler(webapp2.RequestHandler):
+
+ def post(self, project, job):
+ job_key = ndb.Key(urlsafe=job, namespace=project)
+ job = job_key.get()
+ if job.taken:
+ # This job has been previously accepted by someone else.
+ self.response.set_status(409)
+ job.taken = True
+ job.put()
+
+
+app = webapp2.WSGIApplication([
+ ('/', MainHandler),
+ ('/(.*)/push', PushHandler),
+ ('/(.*)/pull', PullHandler),
+ ('/(.*)/peek/?(.*)', PeekHandler),
+ ('/(.*)/accept/(.*)', AcceptHandler),
+])
« no previous file with comments | « chromium-jobqueue/LICENSE ('k') | chromium-jobqueue/app.yaml » ('j') | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698