VVersions.dev

Python 3.12 → 3.14

Python 3.12 is now security-only. The 3.12 → 3.14 jump is moderate: the main work is the PEP 594 stdlib removals and 2to3 removal from 3.13 plus lazy-by-default annotations in 3.14, in exchange for active support, a faster CPython, t-strings, and an officially supported free-threaded build.

Version upgradeDifficulty: moderateEffort: 0.5–3 days for a typical servicemedium risk

Last verified · Updated May 22, 2026

Python 3.12 entered security-only maintenance in April 2025, so move to a supported 3.x. The 3.12 → 3.14 jump crosses two releases: 3.13 removed 19 PEP 594 modules and the 2to3 tool, and 3.14 makes annotations lazy by default (PEP 649/749) and ships the officially supported free-threaded build.

Should you upgrade directly?

Yes. There is no source-incompatible jump that requires stopping at 3.13 first — go straight from 3.12 to 3.14, running CI on 3.14 to surface the removed-module and annotation failures. Keep 3.13 in mind only as a fallback if a dependency lacks 3.14 wheels.

Key differences (3.12 → 3.14, spanning 3.13)

  • PEP 594 removed 19 stdlib modules in 3.13 (cgi, cgitb, telnetlib, nntplib, crypt, imghdr, sndhdr, pipes, aifc, audioop, chunk, mailcap, msilib, nis, ossaudiodev, spwd, sunau, uu, xdrlib).
  • 2to3 and lib2to3 were removed in 3.13 (also tkinter.tix).
  • Annotations are lazy by default in 3.14 (PEP 649/749); read them via annotationlib.get_annotations().
  • Free-threaded (no-GIL) build is officially supported in 3.14 (PEP 779), opt-in as python3.14t.
  • The experimental JIT (PEP 744) now ships in official Windows/macOS binaries, off by default.
  • New features to adopt incrementally: t-strings (PEP 750), compression.zstd, concurrent.interpreters.

Files and patterns to inspect

  • Imports of any PEP 594 module removed in 3.13 (cgi, telnetlib, nntplib, crypt, imghdr, etc.).
  • Build or codemod scripts invoking 2to3 or importing lib2to3.
  • Code reading annotations directly or relying on eager annotation evaluation / get_type_hints.
  • Type-driven libraries (pydantic, dataclasses, attrs, typing-based frameworks) that depend on annotation timing.
  • Pinned dependencies and C extensions that lack Python 3.14 wheels.

⚠ Lazy annotations are the subtle 3.14 risk

The PEP 594 removals fail loudly with ImportError, but lazy annotations (PEP 649/749) fail quietly: code that read annotations at definition time may now see deferred or ForwardRef values. Port introspection to annotationlib.get_annotations() and run your type-driven dependencies' suites on 3.14.

Diagnostic commands

Fail fast on removed-module and deprecation usage

# Recreate the env on 3.14 and surface removed-module/deprecation usage as errors
python3.14 -m venv .venv && . .venv/bin/activate
pip install -e .
python -W error::DeprecationWarning -m pytest -q

Pre-migration checklist

  • Green test suite on Python 3.12
  • Dependencies confirmed to publish Python 3.14 wheels (or 3.13 fallback documented)
  • CI matrix updated to run on 3.14
  • Annotation-dependent libraries identified for targeted testing

Official sources

Copy-ready AI prompts

Structured prompts for an AI coding assistant. Inspect first, then execute incrementally, and keep a human in the review loop.

Repo inspection: Repo inspection prompt

You are helping migrate a Python codebase from Python 3.12 to Python 3.14.

Do not edit files yet. First inspect the repository and report:
1. The exact Python version requirement in setup.py / pyproject.toml / tox.ini / CI config, and the interpreter the project runs on.
2. Python 2-only syntax: print statements, integer-division reliance, except Foo, e: syntax, dict.iteritems/iterkeys/itervalues, xrange, and unicode/str/bytes confusion.
3. Removed/deprecated module usage: distutils, imp, and deprecated collections ABC aliases (collections.Mapping etc.).
4. The dependency manifest (requirements.txt vs lock vs pyproject), any C-extension builds, and pinned versions.
5. The test runner, virtualenv/venv setup, and the install/build/test commands.

Return: a migration risk summary, the files most likely to break, a suggested migration order, the commands to run before editing, and any questions that need human confirmation.

Safety: Inspection only. The agent must not modify files in this step.

Works with Claude Code, Cursor, GitHub Copilot.

Migration execution: Migration execution prompt

Migrate this codebase from Python 3.12 to Python 3.14, one concern at a time.

Work in this order and pause for review after each: (1) create and activate a fresh virtualenv/venv on the target interpreter, (2) run an automated pass with python -m future.utilities futurize (or 2to3) and review the diff, (3) replace removed/deprecated modules (distutils -> setuptools/pyproject, imp -> importlib, collections ABC aliases), (4) fix unicode/bytes boundaries explicitly, (5) reinstall dependencies and resolve pip resolver conflicts.

After each step run pip check and the project's lint and tests, and report results before continuing. Do not refactor unrelated code.

Safety: Apply changes incrementally and keep each step reviewable. Never bundle unrelated refactors.

Works with Claude Code, Cursor, GitHub Copilot.

Test plan

Commands

  • python -m venv .venv && . .venv/bin/activate
  • pip install -e .
  • pip check
  • python -m pytest -q

Manual checks

  • Text/bytes: confirm file and network I/O encode/decode explicitly and round-trips.
  • Division: verify code that relied on Python 2 integer division still produces expected results.
  • C extensions: confirm any compiled dependencies build against the target interpreter.

Regression risks

  • Silent behavior change from true division replacing integer division.
  • Bytes/str mix-ups surfacing only at runtime on non-ASCII input.
  • C-extension dependencies without wheels for the target interpreter.

Acceptance criteria

  • pip check reports no broken requirements and pytest passes on the target version.
  • No imports of distutils, imp, or deprecated collections ABC aliases remain.
  • All dependencies resolve to versions supporting the target Python.

Frequently asked questions

Why upgrade off Python 3.12 specifically?

Python 3.12 entered security-only maintenance on 2025-04-02 (full EOL 2028-10-31) and no longer receives bugfixes. Moving to 3.14 restores active support and brings the faster CPython, t-strings, and the officially supported free-threaded build.

Do I need to stop at 3.13 on the way to 3.14?

No. The 3.12 → 3.14 path is source-compatible enough to do in one hop. Run CI on 3.14 directly; only fall back to 3.13 if a required dependency has not yet published 3.14 wheels.