Dependencies
Core Dependencies
These are the runtime dependencies in the [project] table of pyproject.toml. Flask 3.2.0.dev is built on Werkzeug and Jinja2 and adds a small set of focused libraries.
Web and WSGI layer
werkzeug>=3.1.0is the foundation of the framework and the most widely imported dependency. Its uses by module:- Routing:
flask.sansio.appimportsMap,RuleandBuildError.flask.appimportsMapAdapter,RequestRedirect,RoutingException,RuleandBuildError.flask.ctximportsMapAdapter.flask.debughelpersimportsRequestRedirect.
- HTTP exceptions:
flask.sansio.scaffoldimportsdefault_exceptionsandHTTPException.flask.sansio.appimportsAborter,BadRequestandBadRequestKeyError.flask.appimportsInternalServerError.flask.helpersimportsabort.
- Request/response objects:
flask.wrappersimportsRequest,Response,BadRequest,HTTPExceptionandRule.flask.appandflask.sansio.appimportResponseclasses, andflask.typingandflask.json.providerimportwerkzeug.sansio.response.Response. - Data structures:
flask.appimportsHeadersandImmutableDict.flask.sessionsimportsCallbackDict. - Utilities:
import_stringis imported byflask.cliandflask.config.cached_propertyis imported byflask.sansio.appandflask.sansio.scaffold.redirectis imported byflask.helpersandflask.sansio.app.http_dateis imported byflask.json.providerandflask.json.tag.parse_dateis imported byflask.json.tag.get_hostis imported byflask.app.
- Context proxies:
werkzeug.local.LocalProxyis imported byflask.globalsandflask.logging. - Dev server and testing:
run_simpleandis_running_from_reloaderare imported byflask.appandflask.cli.werkzeug.test.ClientandTestResponseare imported byflask.testing.
- Routing:
Templating and serialization
jinja2>=3.1.2provides templating.flask.templatingimportsEnvironment,Template,BaseLoaderandTemplateNotFound.flask.sansio.scaffoldimportsBaseLoaderandFileSystemLoaderfor template folders.flask.debughelpersusesBaseLoaderin_dump_loader_info()andexplain_template_loading_attempts(), which report which loader tried to locate a template and whether it matched.
markupsafe>=2.1.1suppliesMarkup, whichflask.json.tagimports.itsdangerous>=2.2.0supports sessions.flask.sessionsimportsURLSafeTimedSerializerandBadSignature.
CLI
click>=8.1.3powers theflaskcommand.flask.clibuildscli = FlaskGroup(name="flask", ...), whosemain()callscli.main().flask.cliusesclick.echo()andclick.secho()for output, and importsclick.core.ParameterSource.flask.testingimportsclick.testing.CliRunnerandResult.flask.sansio.scaffoldimportsclick.Grouponly for type checking, undert.TYPE_CHECKING.
Signals
blinker>=1.9.0suppliesNamespace, whichflask.signalsimports. The top-levelflaskpackage re-exports signals such asrequest_started,request_finished,got_request_exception,template_renderedandmessage_flashed.
Optional Dependencies
Two extras are declared under [project.optional-dependencies]:
| Extra | Requirement | Used by |
|---|---|---|
async |
asgiref>=3.2 |
flask.app imports asgiref.sync.async_to_sync |
dotenv |
python-dotenv |
flask.cli imports dotenv |
Install them with pip install "Flask[async]" or pip install "Flask[dotenv]".
flask.helpers has get_load_dotenv(), which reads the FLASK_SKIP_DOTENV environment variable. FlaskGroup takes a load_dotenv option and passes it to ScriptInfo as load_dotenv_defaults.
flask.cli also imports cryptography. It is declared only in the typing dependency group, not among the runtime dependencies or extras.
Development dependency groups
These are declared under [dependency-groups] and are not installed with the package.
| Group | Packages | Purpose |
|---|---|---|
dev |
ruff, tox, tox-uv |
Linting and running test environments |
tests |
asgiref, pytest, python-dotenv |
Test suite, including the async and dotenv paths |
typing |
asgiref, cryptography, mypy, pyright, pytest, python-dotenv, types-contextvars, types-dataclasses |
Type checking with mypy and pyright. The optional dependencies are included so their imports resolve. |
docs |
pallets-sphinx-themes, sphinx<9, sphinx-tabs, sphinxcontrib-log-cabinet |
Documentation build |
docs-auto |
sphinx-autobuild |
Live-rebuilding docs |
pre-commit |
pre-commit, pre-commit-uv |
Git hook management |
gha-update |
gha-update ; python_full_version >= '3.12' |
Updating GitHub Actions versions, only on Python 3.12+ |
Version Requirements
- Python
>=3.10(requires-python). - Runtime minimums:
blinker>=1.9.0click>=8.1.3itsdangerous>=2.2.0jinja2>=3.1.2markupsafe>=2.1.1werkzeug>=3.1.0
- Extras:
asgiref>=3.2.python-dotenvhas no version constraint. - Docs:
sphinx<9is the only upper bound among the dependency groups. - Build:
flit_core>=3.11,<4with backendflit_core.buildapi. - Project version:
3.2.0.dev.
Every runtime dependency uses a lower bound only, with no upper cap. The sphinx<9 cap and the flit_core cap are the only upper-bound constraints in the manifest.
Integration Points
Shared base class
Scaffold in flask.sansio.scaffold is the common base for Flask and Blueprint. It is where Jinja2's FileSystemLoader, Werkzeug's default_exceptions and cached_property, and the typed decorators (T_route, T_error_handler, and so on) come together. The @setupmethod decorator wraps registration methods and calls _check_setup_finished() first.
Blueprint in flask.sansio.blueprints implements _check_setup_finished() to raise an AssertionError once the blueprint has been registered, so setup changes cannot be applied inconsistently.
Sans-IO split
flask.sansio.app holds the application state that depends on Werkzeug's Map, Rule, Aborter and sansio Response. flask.app adds the WSGI-specific pieces: run_simple, MapAdapter, get_host, and the optional async_to_sync.
Thin wrappers over Werkzeug
flask.helpersimports Werkzeug'sabortandredirectunder the private aliases_wz_abortand_wz_redirect, and re-exposesabortandredirectfrom the top-levelflaskpackage.flask.globalsbuildscurrent_app,g,requestandsessiononLocalProxy, andflask.loggingalso usesLocalProxy.flask.wrappersprovides the framework'sRequestandResponseon top of Werkzeug's.
CLI
FlaskGroup in flask.cli extends Click's group behavior.
make_context()setsFLASK_RUN_FROM_CLI=truesoapp.run()becomes a no-op while a CLI command runs.make_context()also creates aScriptInfoas the context object when none is supplied.list_commands()merges in commands from the loaded app'scli. ANoAppExceptionprints only the error message in red, and any other exception prints the full traceback.parse_args()handles--env-fileand--appearly, so help output can includeapp.clicommands.- The
routescommand formatsurl_maprules into a table withclick.echo().
cli = FlaskGroup(name="flask", help="A general utility script for Flask applications. ...")
def main() -> None:
cli.main()
Sessions, signals and JSON
flask.sessionscombinesURLSafeTimedSerializerandBadSignaturefromitsdangerouswith Werkzeug'sCallbackDict.flask.signalscreates its signals fromblinker.Namespace.flask.json.tagcombinesmarkupsafe.Markupwith Werkzeug'shttp_dateandparse_date.
Testing
flask.testing builds on werkzeug.test.Client, werkzeug.wrappers.Request and click.testing.CliRunner, so tests can exercise both the WSGI app and CLI commands.