app = tornado.web.Application([
url(r"/photos/(.*)", MyPhotoHandler),
url(r"/pictures/(.*)", tornado.web.RedirectHandler,
- dict(url=r"/photos/\1")),
+ dict(url=r"/photos/{0}")),
])
Unlike `.RequestHandler.redirect`, `.RedirectHandler` uses permanent
def test_reverse_arguments(self):
self.assertEqual('/api/v1/foo/bar',
url(r'^/api/v1/foo/(\w+)$', None).reverse('bar'))
+
+
+class RedirectHandlerTest(WebTestCase):
+ def get_handlers(self):
+ return [
+ ('/src', WebRedirectHandler, {'url': '/dst'}),
+ (r'/(.*?)/(.*?)/(.*)', WebRedirectHandler, {'url': '/{1}/{0}/{2}'})]
+
+ def test_basic_redirect(self):
+ response = self.fetch('/src', follow_redirects=False)
+ self.assertEqual(response.code, 301)
+ self.assertEqual(response.headers['Location'], '/dst')
+
+ def test_redirect_pattern(self):
+ response = self.fetch('/a/b/c', follow_redirects=False)
+ self.assertEqual(response.code, 301)
+ self.assertEqual(response.headers['Location'], '/b/a/c')
application = web.Application([
(r"/oldpath", web.RedirectHandler, {"url": "/newpath"}),
])
+
+ `RedirectHandler` supports regular expression substitutions. E.g., to
+ swap the first and second parts of a path while preserving the remainder::
+
+ application = web.Application([
+ (r"/(.*?)/(.*?)/(.*)", web.RedirectHandler, {"url": "/{1}/{0}/{2}"}),
+ ])
+
+ The final URL is formatted with `str.format` and the substrings that match
+ the capturing groups. In the above example, a request to "/a/b/c" would be
+ formatted like::
+
+ str.format("/{1}/{0}/{2}", "a", "b", "c") # -> "/b/a/c"
+
+ Use Python's :ref:`format string syntax <formatstrings>` to customize how
+ values are substituted.
"""
def initialize(self, url, permanent=True):
self._url = url
self._permanent = permanent
- def get(self):
- self.redirect(self._url, permanent=self._permanent)
+ def get(self, *args):
+ self.redirect(self._url.format(*args), permanent=self._permanent)
class StaticFileHandler(RequestHandler):