# What’s new in Tornado 3.1

## Jun 15, 2013

### Multiple modules

- Many reference cycles have been broken up throughout the package, allowing for more efficient garbage collection on CPython.
- Silenced some log messages when connections are opened and immediately closed (i.e. port scans), or other situations related to closed connections.
- Various small speedups: `HTTPHeaders` case normalization, `UIModule` proxy objects, precompile some regexes.

### `tornado.auth`

- `OAuthMixin` always sends `oauth_version=1.0` in its request as required by the spec.
- `FacebookGraphMixin` now uses `self._FACEBOOK_BASE_URL` in `facebook_request` to allow the base url to be overridden.
- The `authenticate_redirect` and `authorize_redirect` methods in the `tornado.auth` mixin classes all now return Futures. These methods are asynchronous in `OAuthMixin` and derived classes, although they do not take a callback. The `Future` these methods return must be yielded if they are called from a function decorated with `gen.coroutine` (but not `gen.engine`).
- `TwitterMixin` now uses `/account/verify_credentials` to get information about the logged-in user, which is more robust against changing screen names.
- The `demos` directory (in the source distribution) has a new `twitter` demo using `TwitterMixin`.

### `tornado.escape`

- `url_escape` and `url_unescape` have a new `plus` argument (defaulting to True for consistency with the previous behavior) which specifies whether they work like `urllib.parse.unquote` or `urllib.parse.unquote_plus`.

### `tornado.gen`

- Fixed a potential memory leak with long chains of `tornado.gen` coroutines.

### `tornado.httpclient`

- `tornado.httpclient.HTTPRequest` takes a new argument `auth_mode`, which can be either `basic` or `digest`. Digest authentication is only supported with `tornado.curl_httpclient`.
- `tornado.curl_httpclient` no longer goes into an infinite loop when pycurl returns a negative timeout.
- `curl_httpclient` now supports the `PATCH` and `OPTIONS` methods without the use of `allow_nonstandard_methods=True`.
- Worked around a class of bugs in libcurl that would result in errors from `IOLoop.update_handler` in various scenarios including digest authentication and socks proxies.
- The `TCP_NODELAY` flag is now set when appropriate in `simple_httpclient`.
- `simple_httpclient` no longer logs exceptions, since those exceptions are made available to the caller as `HTTPResponse.error`.

### `tornado.httpserver`

- `tornado.httpserver.HTTPServer` handles malformed HTTP headers more gracefully.
- `HTTPServer` now supports lists of IPs in `X-Forwarded-For` (it chooses the last, i.e. nearest one).
- Memory is now reclaimed promptly on CPython when an HTTP request fails because it exceeded the maximum upload size.
- The `TCP_NODELAY` flag is now set when appropriate in `HTTPServer`.
- The `HTTPServer` `no_keep_alive` option is now respected with HTTP 1.0 connections that explicitly pass `Connection: keep-alive`.
- The `Connection: keep-alive` check for HTTP 1.0 connections is now case-insensitive.
- The `str` and `repr` of `tornado.httpserver.HTTPRequest` no longer include the request body, reducing log spam on errors (and potential exposure/retention of private data).

### `tornado.httputil`

- The cache used in `HTTPHeaders` will no longer grow without bound.

### `tornado.ioloop`

- Some `IOLoop` implementations (such as `pyzmq`) accept objects other than integer file descriptors; these objects will now have their `.close()` method called when the `IOLoop` is closed with ``all_fds=True`.
- The stub handles left behind by `IOLoop.remove_timeout` will now get cleaned up instead of waiting to expire.

### `tornado.iostream`

- Fixed a bug in `BaseIOStream.read_until_close` that would sometimes cause data to be passed to the final callback instead of the streaming callback.
- The `IOStream` close callback is now run more reliably if there is an exception in `_try_inline_read`.
- New method `BaseIOStream.set_nodelay` can be used to set the `TCP_NODELAY` flag.
- Fixed a case where errors in `SSLIOStream.connect` (and `SimpleAsyncHTTPClient`) were not being reported correctly.

### `tornado.locale`

- `Locale.format_date` now works on Python 3.

### `tornado.netutil`

- The default `Resolver` implementation now works on Solaris.
- `Resolver` now has a `close` method.
- Fixed a potential CPU DoS when `tornado.netutil.ssl_match_hostname` is used on certificates with an abusive wildcard pattern.
- All instances of `ThreadedResolver` now share a single thread pool, whose size is set by the first one to be created (or the static `Resolver.configure` method).
- `ExecutorResolver` is now documented for public use.
- `bind_sockets` now works in configurations with incomplete IPv6 support.

### `tornado.options`

- `tornado.options.define` with `multiple=True` now works on Python 3.
- `tornado.options.options` and other `OptionParser` instances support some new dict-like methods: `items()`, iteration over keys, and (read-only) access to options with square braket syntax. `OptionParser.group_dict` returns all options with a given group name, and `OptionParser.as_dict` returns all options.

### `tornado.process`

- `tornado.process.Subprocess` no longer leaks file descriptors into the child process, which fixes a problem in which the child could not detect that the parent process had closed its stdin pipe.
- `Subprocess.set_exit_callback` now works for subprocesses created without an explicit `io_loop` parameter.

### `tornado.stack_context`

- `tornado.stack_context` has been rewritten and is now much faster.
- New function `run_with_stack_context` facilitates the use of stack contexts with coroutines.

### `tornado.tcpserver`

- The constructors of `TCPServer` and `HTTPServer` now take a `max_buffer_size` keyword argument.

### `tornado.template`

- Some internal names used by the template system have been changed; now all “reserved” names in templates start with `_tt_`.

### `tornado.testing`

- `tornado.testing.AsyncTestCase.wait` now raises the correct exception when it has been modified by `tornado.stack_context`.
- `tornado.testing.gen_test` can now be called as `@gen_test(timeout=60)` to give some tests a longer timeout than others.
- The environment variable `ASYNC_TEST_TIMEOUT` can now be set to override the default timeout for `AsyncTestCase.wait` and `gen_test`.
- `bind_unused_port` now passes `None` instead of `0` as the port to `getaddrinfo`, which works better with some unusual network configurations.

### `tornado.util`

- `tornado.util.import_object` now works with top-level module names that do not contain a dot.
- `tornado.util.import_object` now consistently raises `ImportError` instead of `AttributeError` when it fails.

### `tornado.web`

- The `handlers` list passed to the `tornado.web.Application` constructor and `add_handlers` methods can now contain lists in addition to tuples and `URLSpec` objects.
- `tornado.web.StaticFileHandler` now works on Windows when the client passes an `If-Modified-Since` timestamp before 1970.
- New method `RequestHandler.log_exception` can be overridden to customize the logging behavior when an exception is uncaught. Most apps that currently override `_handle_request_exception` can now use a combination of `RequestHandler.log_exception` and `write_error`.
- `RequestHandler.get_argument` now raises `MissingArgumentError` (a subclass of `tornado.web.HTTPError`, which is what it raised previously) if the argument cannot be found.
- `Application.reverse_url` now uses `url_escape` with `plus=False`, i.e. spaces are encoded as `%20` instead of `+`.
- Arguments extracted from the url path are now decoded with `url_unescape` with `plus=False`, so plus signs are left as-is instead of being turned into spaces.
- `RequestHandler.send_error` will now only be called once per request, even if multiple exceptions are caught by the stack context.
- The `tornado.web.asynchronous` decorator is no longer necessary for methods that return a `Future` (i.e. those that use the `gen.coroutine` or `return_future` decorators)
- `RequestHandler.prepare` may now be asynchronous if it returns a `Future`. The `asynchronous` decorator is not used with `prepare`; one of the `Future`-related decorators should be used instead.
- `RequestHandler.current_user` may now be assigned to normally.
- `RequestHandler.redirect` no longer silently strips control characters and whitespace. It is now an error to pass control characters, newlines or tabs.
- `StaticFileHandler` has been reorganized internally and now has additional extension points that can be overridden in subclasses.
- `StaticFileHandler` now supports HTTP `Range` requests. `StaticFileHandler` is still not suitable for files too large to comfortably fit in memory, but `Range` support is necessary in some browsers to enable seeking of HTML5 audio and video.
- `StaticFileHandler` now uses longer hashes by default, and uses the same hashes for `Etag` as it does for versioned urls.
- `StaticFileHandler.make_static_url` and `RequestHandler.static_url` now have an additional keyword argument `include_version` to suppress the url versioning.
- `StaticFileHandler` now reads its file in chunks, which will reduce memory fragmentation.
- Fixed a problem with the `Date` header and cookie expiration dates when the system locale is set to a non-english configuration.

### `tornado.websocket`

- `WebSocketHandler` now catches `StreamClosedError` and runs `on_close` immediately instead of logging a stack trace.
- New method `WebSocketHandler.set_nodelay` can be used to set the `TCP_NODELAY` flag.

### `tornado.wsgi`

- Fixed an exception in `WSGIContainer` when the connection is closed while output is being written.