A bunch of releases from the Pallets projects
May 11 marked a new major release for the Python-based Flask web microframework project, but Flask 2.0 was only part of the story. While the framework may be the most visible piece, it is one of a small handful of cooperating libraries that provide solutions for various web-development tasks; all are incorporated into the Pallets projects organization. For the first time, all six libraries that make up Pallets were released at the same time and each had a new major version number. In part, that new major version indicated that Python 2 support was being left behind, but there is plenty more that went into the coordinated release.
Pallets
While Flask is pretty well-known and has even been written about here before, the Pallets umbrella organization has flown a bit under the radar, at least for me. The Jinja2 template engine, a Pallets component that is used by Flask, is also fairly high-profile, but the other pieces of the puzzle are less so. The only other Pallets library I had heard of was the Werkzeug library for supporting Web Server Gateway Interface (WSGI) applications. It is used to connect Flask applications to web servers.
There are three more libraries on the pallet, but those are smaller and
more specialized: MarkupSafe, which
provides a text object that escapes characters interpreted by HTML, ItsDangerous, which
provides helpers to cryptographically sign data that will be moved between
trusted and untrusted environments, and
the
Command Line Interface
Creation Kit, or Click, which is used for "creating beautiful command line interfaces in a composable way with as little code as necessary
". The
coordinated release was
announced
on the Pallets blog; it is based on two years of work, though there have
been other fairly substantial releases in that time span (e.g. Flask 1.1
in July 2019, Jinja 2.11
in January 2020, Werkzeug 1.0
in February 2020). Beyond Flask 2.0, which was mentioned above, the
release also included:
All of the projects now only support Python 3.6 and above, which was
something that Pallets had announced
back at the end of 2019. "Removing the compatibility code makes the
code faster, as well as easier to maintain and contribute to.
"
Another cross-release feature is type
annotations that have been added throughout the libraries. Beyond that, various tools have been
used to enforce a consistent style on the entire code base.
Changes
Flask now supports asynchronous views and error handlers, so those functions can be defined with async def and Flask will run them in a separate thread. It is not entirely clear how much additional support for async will be added to Flask, as the Quart project already provides an asynchronous web framework with the Flask API. Quart developer Philip Jones is one of the Pallets maintainers; he wrote a blog post about the subject and filed the GitHub issue on async for Flask back in 2019.
Blueprints can now be nested in Flask 2.0, which affords more flexibility in organizing a web application. The development server (i.e. "flask run") has better error handling and no longer defers errors that are detected when it starts up. The "flask shell", which provides a Python read-eval-print loop (REPL) within the context of the Flask application, now has tab completion when Readline is available.
The highlights for Werkzeug 2.0 contain several features that make it
more flexible for supporting async. Local variables are managed with the ContextVar
type so that they can be shared between coroutines and not just threads.
The Flask Request
and Response
classes have been refactored to remove the
BaseRequest/Response parent classes and moved all of the
mixins into those (now) base classes. In
addition, a new API
is being created that removes the code that is WSGI- or
I/O-dependent from those
classes. "This will allow us to better support sync and async use cases
in the future.
" In particular, it will allow Quart and other Asynchronous Server Gateway
Interface (ASGI) frameworks to use Werkzeug.
In addition, many of the datetime objects returned from Werkzeug are now time-zone-aware. The parsing of multipart/form-data, which is used for file uploads, has been improved significantly, leading to up to 15x better performance. The URL routing now understands WebSocket schemes (ws:// and wss://); the library does not have support for WebSocket directly, but this feature will allow projects to use the Werkzeug routing.
Support for async environments and rendering no longer requires patching Jinja with the release of version 3.0. In addition, the NativeEnvironment, which allows templates to produce native Python types rather than only strings, has also been fixed to support async environments. Blocks in templates can now be marked as required, which means they must be defined somewhere in the template hierarchy. Translation contexts (via pggettext and npgettext) can now be used to determine translation strings in the i18n extension.
Click 8.0 brings a bunch of improvements to argument handling, which makes
sense for a toolkit to build command-line tools. The tab completion
feature has been completely rewritten in order to allow each
"command, group, parameter, and type to provide custom
completion
"; completion has other improvements as well. Support has been
added for colors specified by the 256-color palette or using RGB values,
as has the ability to do italics, strike-through, and other text effects.
Help text formatting has been improved and messages for users are now
able to be translated.
ItsDangerous, which provides an easy-to-use mechanism to generate signatures for things like cookie values, has added support for key rotation in version 2.0. A list of keys can be passed, from oldest to newest; the newest will be used for signing, while all of the keys will be tried when verifying the signature. It has also made its datetime objects time-zone-aware. MarkupSafe 2.0 added a whole slew of binary wheels for various different combinations of Python version, operating system, and architecture—33 in all.
This overview just touches on some of the changes in these libraries that caught my eye. Looking at the announcement in more detail, as well as the highly detailed changelogs, will fill in lots of other details on improvements that have been made.
History
Beyond providing a nice set of tools that can be used in the development of web applications, the Pallets projects have another thing in common: they all were started by Armin Ronacher, who has been a prolific contributor in the Python community. He introduced the Pallets projects in a blog post exactly six years after he released an April Fools joke that turned into Flask:
On the first of April 2010, I released a joke microframework called denied which made fun of the fact that all microframeworks at the time decided to forgo with dependencies and bundle up everything they need in a single Python file. What I did was embed all of Jinja2 and Werkzeug in a base64 encoded zip file within the framework's only Python file. The response to it was interesting in a few ways because on the one hand quite a few people did not really understand that it was an April fools joke to begin with and on the other, there was a discussion where there were no microframeworks that actually did use dependencies and encouraged it.One month later there was a new project by the name of "Flask" which actually gave this concept a real shot. It launched with the tagline "a microframework for Python based on Werkzeug, Jinja 2 and good intentions" and six years later it's the most starred Python framework on GitHub.
Ronacher is still part of
Pallets today, along with the three people he started it with and
others, like Jones, who have joined since. Those seven listed people
are, naturally, backed up by lots of others: "The total list of
people involved is much larger as they consist of countless of
contributions of many individuals over the years.
" As with pretty
much every project (or set of projects) out there, Pallets would be happy
to have more contributors should any of the libraries pique the interest of
any readers.
| Index entries for this article | |
|---|---|
| Python | Libraries |
| Python | Web |
