Skip to content
Browse files

trying to handle signals better

  • Loading branch information...
1 parent 5c51567 commit 5c014e87198408aeeef02892ccc1edb713d9c484 @gabrielfalcao committed Mar 9, 2011
Showing with 49 additions and 5 deletions.
  1. +12 −0 lettuce/django/management/commands/harvest.py
  2. +37 −5 lettuce/django/server.py
View
12 lettuce/django/management/commands/harvest.py
@@ -16,6 +16,7 @@
# along with this program. If not, see <http://www.gnu.org/licenses/>.
import os
import sys
+import signal
from optparse import make_option
from django.conf import settings
from django.core.management.base import BaseCommand
@@ -54,6 +55,7 @@ class Command(BaseCommand):
help='Comma separated list of scenarios to run'),
)
def stopserver(self, failed=False):
+ server.stop(fail=failed)
raise SystemExit(int(failed))
def get_paths(self, args, apps_to_run, apps_to_avoid):
@@ -69,7 +71,17 @@ def get_paths(self, args, apps_to_run, apps_to_avoid):
return paths
+ def handle_control_c(self, signum, frame):
+ print "oops, aborting..."
+ server.stop(fail=True)
+ print 'harvest aborted, no crops for this spring :('
+ sys.exit(2)
+
def handle(self, *args, **options):
+ signal.signal(signal.SIGABRT, self.handle_control_c)
+ signal.signal(signal.SIGTERM, self.handle_control_c)
+ signal.signal(signal.SIGINT, self.handle_control_c)
+
setup_test_environment()
settings.DEBUG = options.get('debug', False)
View
42 lettuce/django/server.py
@@ -63,6 +63,10 @@ def log_message(self, *args, **kw):
def handle(self):
"""Handle a single HTTP request"""
+ global keep_running
+ if not keep_running:
+ return
+
self.raw_requestline = self.rfile.readline()
if not self.parse_request(): # An error code has been sent, just exit
return
@@ -73,11 +77,18 @@ def handle(self):
self.dev_null,
self.get_environ()
)
+ if not keep_running:
+ return
+
handler.request_handler = self # backpointer for logging
handler.run(self.server.get_app())
class LettuceServerHandler(ServerHandler):
def finish_response(self):
+ global keep_running
+ if not keep_running:
+ return
+
try:
ServerHandler.finish_response(self)
@@ -109,11 +120,13 @@ def get_real_address(address):
def wait(self):
address = ThreadedServer.get_real_address(self.address)
- while True:
- time.sleep(0.1)
+ while keep_running:
+ time.sleep(1)
http = httplib.HTTPConnection(address, self.port)
try:
http.request("GET", "/")
+ self.lock.release()
+
except socket.error:
http.close()
continue
@@ -122,6 +135,8 @@ def wait(self):
self.lock.acquire()
def run(self):
+ global keep_running
+
self.lock.acquire()
pidfile = os.path.join(tempfile.gettempdir(), 'lettuce-django.pid')
if os.path.exists(pidfile):
@@ -141,9 +156,11 @@ def run(self):
max_port = 65535
connector = socket.socket(socket.AF_INET, socket.SOCK_STREAM)
- while not bound or self.port < max_port:
+ while keep_running and (not bound or self.port < max_port):
+ time.sleep(1)
try:
connector.connect((self.address, self.port))
+
self.port += 1
except socket.error:
@@ -169,16 +186,28 @@ def run(self):
if 'django.contrib.admin' in settings.INSTALLED_APPS:
admin_media_path = ''
handler = AdminMediaHandler(handler, admin_media_path)
- print "Preparing to server django's admin site static files..."
+ print "Preparing to serve django's admin site static files..."
httpd.set_app(handler)
- global keep_running
while keep_running:
+ time.sleep(1)
+
call_hook('before', 'handle_request', httpd, self)
+
+
+ # timeout http://bugs.python.org/issue1167930 between big
+ # amounts of CPU usage
+
+ time.sleep(1) # part 1
+
httpd.handle_request()
+
+ time.sleep(1) # part 2
+
call_hook('after', 'handle_request', httpd, self)
if self.lock.locked():
+ time.sleep(1)
self.lock.release()
class Server(object):
@@ -202,6 +231,9 @@ def start(self):
print "Django's builtin server is running at %s:%d" % addrport
def stop(self, fail=False):
+ global keep_running
+ keep_running = False
+
http = httplib.HTTPConnection(self.address, self.port)
try:
http.request("DELETE", "/")

0 comments on commit 5c014e8

Please sign in to comment.
Something went wrong with that request. Please try again.