Commits

Robert Brewer committed 6670bb3

Moved request.handler from a function (with vpath, and request.params included in cell refs) to an instance of a callable PageHandler class (with vpath, params included as .args, .kwargs attributes). Instances of HTTPRedirect and HTTPError (including NotFound) can now also be set directly as request.handler (they raise self when called).

Comments (0)

Files changed (2)

             response.body = None
         else:
             raise ValueError("The %s status code is unknown." % status)
+    
+    def __call__(self):
+        # Allow the exception to be used as a request.handler.
+        raise self
 
 
 class HTTPError(Exception):
         response.headers['Content-Type'] = "text/html"
         
         _be_ie_unfriendly(self.status)
+    
+    def __call__(self):
+        # Allow the exception to be used as a request.handler.
+        raise self
 
 
 class NotFound(HTTPError):
         response.status, response.header_list, response.body = r
 
 
+class PageHandler(object):
+    """Callable which sets response.body."""
+    
+    def __init__(self, callable, *args, **kwargs):
+        self.callable = callable
+        self.args = args
+        self.kwargs = kwargs
+    
+    def __call__(self):
+        cherrypy.response.body = self.callable(*self.args, **self.kwargs)
+
+
+class LateParamPageHandler(PageHandler):
+    
+    def __getattribute__(self, name):
+        attr = object.__getattribute__(self, name)
+        if name == "kwargs":
+            if attr:
+                kwargs = cherrypy.request.params.copy()
+                kwargs.update(attr)
+            else:
+                kwargs = cherrypy.request.params
+            return kwargs
+        else:
+            return attr
+
+
 class Dispatcher(object):
     
     def __call__(self, path_info):
         vpath = [x.replace("%2F", "/") for x in vpath]
         
         if func:
-            def handler():
-                cherrypy.response.body = func(*vpath, **request.params)
-            request.handler = handler
+            request.handler = LateParamPageHandler(func, *vpath)
         else:
-            def notfound():
-                raise cherrypy.NotFound()
-            request.handler = notfound
+            request.handler = cherrypy.NotFound()
     
     def find_handler(self, path):
         """Find the appropriate page handler for the given path."""
             if func is None and meth == "HEAD":
                 func = getattr(resource, "GET", None)
             if func:
-                def handler():
-                    cherrypy.response.body = func(*vpath, **request.params)
-                request.handler = handler
-                return
+                request.handler = LateParamPageHandler(func, *vpath)
             else:
-                def notallowed():
-                    raise cherrypy.HTTPError(405)
-                request.handler = notallowed
+                request.handler = cherrypy.HTTPError(405)
         else:
-            def notfound():
-                raise cherrypy.NotFound()
-            request.handler = notfound
+            request.handler = cherrypy.NotFound()
 
 
 def fileGenerator(input, chunkSize=65536):
Tip: Filter by directory path e.g. /media app.js to search for public/media/app.js.
Tip: Use camelCasing e.g. ProjME to search for ProjectModifiedEvent.java.
Tip: Filter by extension type e.g. /repo .js to search for all .js files in the /repo directory.
Tip: Separate your search with spaces e.g. /ssh pom.xml to search for src/ssh/pom.xml.
Tip: Use ↑ and ↓ arrow keys to navigate and return to view the file.
Tip: You can also navigate files with Ctrl+j (next) and Ctrl+k (previous) and view the file with Ctrl+o.
Tip: You can also navigate files with Alt+j (next) and Alt+k (previous) and view the file with Alt+o.