Save references to wrapped functions.
[wrw.git] / wrw / dispatch.py
... / ...
CommitLineData
1import sys, traceback
2import env, req, proto
3
4__all__ = ["restart"]
5
6class restart(Exception):
7 def handle(self, req):
8 pass
9
10def mangle(result):
11 try:
12 iter(result)
13 except TypeError:
14 pass
15 else:
16 return result
17 return [str(result)]
18
19def defaulterror(req, excinfo):
20 import resp
21 traceback.print_exception(*excinfo)
22 raise resp.httperror(500)
23
24def wraphandler(handler, excinfo):
25 def wrapped(req):
26 return handler(req, excinfo)
27 wrapped.__wrapped__ = handler
28 return wrapped
29
30errorhandler = env.var(defaulterror)
31
32def handle(req, startreq, handler):
33 eh = errorhandler.val
34 try:
35 resp = [""]
36 while True:
37 try:
38 resp = handler(req)
39 break
40 except restart, i:
41 handler = i.handle
42 except Exception, i:
43 if eh is None:
44 raise
45 handler = wraphandler(eh, sys.exc_info())
46 eh = None
47 req.commit(startreq)
48 return resp
49 finally:
50 req.cleanup()
51
52def handleenv(env, startreq, handler):
53 if not "HTTP_HOST" in env:
54 return proto.simpleerror(env, startreq, 400, "Bad Request", "Request must include Host header.")
55 r = req.origrequest(env)
56 return handle(r, startreq, handler)