- This is the last release of Tornado to support Python 3.5. Future versions will require Python 3.6 or newer.
- Windows support has been improved. Tornado is now compatible with the proactor event loop (which became the default in Python 3.8) by automatically falling back to running a selector in a second thread. This means that it is no longer necessary to explicitly configure a selector event loop, although doing so may improve performance. This does not change the fact that Tornado is significantly less scalable on Windows than on other platforms.
- Binary wheels are now provided for Windows, MacOS, and Linux (amd64 and arm64).
- .coroutine now has better support for the Python 3.7+
contextvars
module. In particular, theContextVar.reset
method is now supported.
HEAD
requests to handlers that used chunked encoding no longer produce malformed output.- Certain kinds of malformed
gzip
data no longer cause an infinite loop.
- Setting
decompress_response=False
now works correctly withcurl_httpclient
. - Mixing requests with and without proxies works correctly in
curl_httpclient
(assuming the version of pycurl is recent enough). - A default
User-Agent
ofTornado/$VERSION
is now used if theuser_agent
parameter is not specified. - After a 303 redirect,
tornado.simple_httpclient
always usesGET
. Previously this would useGET
if the original request was aPOST
and would otherwise reuse the original request method. Forcurl_httpclient
, the behavior depends on the version oflibcurl
(with the most recent versions usingGET
after 303 regardless of the original method). - Setting
request_timeout
and/orconnect_timeout
to zero is now supported to disable the timeout.
- Header parsing is now faster.
- .parse_body_arguments now accepts incompletely-escaped non-ASCII inputs.
- ssl.CertificateError during the SSL handshake is now handled correctly.
- Reads that are resolved while the stream is closing are now handled correctly.
- When colored logging is enabled,
logging.CRITICAL
messages are now recognized and colored magenta.
EADDRNOTAVAIL
is now ignored when binding tolocalhost
with IPv6. This error is common in docker.
- .AnyThreadEventLoopPolicy now also configures a selector event loop for these threads (the proactor event loop only works on the main thread)
- The
set_close_exec
function has been removed.
- .ExpectLog now has a
level
argument to ensure that the given log level is enabled.
RedirectHandler.get
now accepts keyword arguments.- When sending 304 responses, more headers (including
Allow
) are now preserved. reverse_url
correctly handles escaped characters in the regex route.- Default
Etag
headers are now generated with SHA-512 instead of MD5.
- The
ping_interval
timer is now stopped when the connection is closed. - .websocket_connect now raises an error when it encounters a redirect instead of hanging.