Files
UmbraEdit/UMBRAEDIT_UPDATE_PLAN.md
B.D. Murphy 1728fc31ed
Some checks failed
Syntax / Linting and Type Checking (push) Has been cancelled
Tests / Linux Python 3.11 (push) Has been cancelled
Tests / Linux Python 3.12 (push) Has been cancelled
Tests / Linux Python 3.13 (push) Has been cancelled
Tests / Linux Python 3.14 (push) Has been cancelled
Tests / Linux Python 3.15 (push) Has been cancelled
Tests / MacOS Python 3.14 (push) Has been cancelled
Tests / Windows Python 3.14 (push) Has been cancelled
Tests / PR Coverage Report (push) Has been cancelled
Tests / Action Coverage Report (push) Has been cancelled
Tests / Ubuntu 24.04 & Sys Packages (push) Has been cancelled
Tests / Fedora 44 & Sys Packages (push) Has been cancelled
docs: add B.D. Murphy 2026 copyright and change comments to modified files
- Confirm original copyright (Veronica Berglyd Olsen) preserved in all modified files
- Add Additional Copyright (C) 2026 B.D. Murphy to:
  - umbraedit/__init__.py (version/date/hexversion changes)
  - umbraedit/splash.py (SPLASH_IMG path change)
  - umbraedit/guimain.py (app icon change to UmbraEdit.jpg)
  - umbraedit/gui/theme.py (icon resolution change)
  - umbraedit/assets/images/umbraedit-text-light.svg (replaced novelWriter text)
  - umbraedit/assets/images/umbraedit-text-dark.svg (replaced novelWriter text)
  - CHANGELOG.md (1.0.0 release entry)
  - .gitignore (exclude accidentally committed files)
  - UMBRAEDIT.md, UMBRAEDIT_UPDATE_PLAN.md, UmbraEdit.command (new files)
- Add inline change comments describing each modification
2026-11-05 09:07:29 -08:00

8.4 KiB

UmbraEdit — Toolchain & Dependency Update Plan

Copyright (C) 2026 B.D. Murphy. Plan for upgrading UmbraEdit (Python/PyQt6) toolchain and dependencies.

Goal: Bring UmbraEdit (Python/PyQt6) up to the latest stable versions of its tools and dependencies, starting from the current baseline.

Baseline (as of 2026-11-05):

  • System Python: 3.9.6 (/usr/bin/python3) — below the project's requires-python >=3.11
  • Available runtimes: Python 3.11.15, 3.12.13 (via uv in ~/.local/bin)
  • uv: 0.11.7 (2026-04-15) — outdated
  • PyQt6: not yet installed in the 3.11 environment
  • pyproject.toml deps: pyqt6>=6.4, pyenchant>=3.3.0, pyobjc-framework-Cocoa (darwin)
  • Lockfile: uv.lock (references novelwriter package name — will need regen)

1. Target Versions

Tool Current Target Source
Python runtime 3.9.6 (system) 3.12.x (latest 3.12) or 3.13.x uv / python.org
PyQt6 not installed latest 6.x PyPI
pyenchant >=3.3.0 latest 3.x PyPI
pyobjc-framework-Cocoa pinned by pyproject latest (macOS only) PyPI
uv 0.11.7 latest github.com/astral-sh/uv
ruff (in uv.lock) latest PyPI
pyright (in uv.lock) latest npm/PyPI
pytest (in uv.lock) latest 8.x PyPI
pytest-qt (in uv.lock) latest PyPI
coverage (in uv.lock) latest PyPI
Sphinx + theme (in uv.lock) latest PyPI
setuptools 82.0.1 latest PyPI
pip 26.0.1 latest ensure via uv

Prefer Python 3.12 as the primary target (mature, PyQt6 wheels widely available). Keep 3.11 as a secondary CI matrix entry since requires-python is >=3.11.


2. Phased Execution

Phase 0 — Preparation & Safety

  1. Ensure working tree is clean and all changes committed on main (already done).
  2. Tag the current state as a rollback point:
    git tag umbraedit/pre-toolchain-update
    git push origin umbraedit/pre-toolchain-update
    
  3. Record current working commands (python3 UmbraEdit.py, test runner) so you can compare before/after.
  4. Back up uv.lock and pyproject.toml.

Phase 1 — Upgrade uv and Python runtimes

  1. Upgrade uv itself:
    uv self upgrade
    # or: curl -LsSf https://astral.sh/uv/install.sh | sh
    
  2. Install the target Python(s) via uv (so they are isolated and reproducible):
    uv python install 3.12
    uv python install 3.11   # keep for CI matrix
    uv python list
    uv python pin 3.12        # sets default for this project (writes .python-version)
    
  3. Verify:
    uv run python --version   # should report 3.12.x
    

Phase 2 — Upgrade core runtime dependencies

Create a fresh virtual environment with the target Python and install the project's runtime deps at their latest compatible versions:

cd /Volumes/1TB_APL_Storage/novelWriter2
uv venv --python 3.12
uv pip install "pyqt6>=6.4" "pyenchant>=3.3.0"
# macOS only:
uv pip install "pyobjc-framework-Cocoa"

Then:

  1. Run the app to confirm it starts:
    uv run python UmbraEdit.py
    # or, after venv activation:
    python UmbraEdit.py
    
  2. If pyqt6 wheels fail on the target Python, fall back to 3.11 or file an issue.

Phase 3 — Upgrade build / lint / test tooling

Update the dependency groups in pyproject.toml (build, docs, test, lint) to latest, then sync:

[dependency-groups]
dev = [
    { include-group = "build" },
    { include-group = "docs" },
    { include-group = "test" },
    { include-group = "lint" },
]
build = ["pyyaml", "tzdata; sys_platform == 'win32'"]
docs = [
    "docutils>=0.17.1",
    "pygments>=2.7",
    "sphinx-book-theme",
    "sphinx-copybutton",
    "sphinx-design",
    "sphinx-favicon",
    "sphinx-intl",
    "sphinx>=5.0",
]
test = [
    "coverage>=7.16.0",
    "pytest-qt",
    "pytest-timeout",
    "pytest>=6.0.0",
    "tzdata; sys_platform == 'win32'",
]
lint = ["pyright", "ruff"]

Suggested edits:

  • Bump pytest>=6.0.0 → pytest>=8.0 (check PyPI for latest 8.x)
  • Bump coverage>=7.16.0 → latest
  • Bump sphinx>=5.0 → latest 7.x/8.x
  • Keep ruff and pyright unpinned or with generous lower bounds so uv lock resolves latest

Then sync:

uv lock --upgrade       # resolve all groups to latest
uv sync --all-groups    # create .venv with everything

Phase 4 — Regenerate uv.lock

uv.lock currently references the old novelwriter package name and is stale.

uv lock --upgrade
git diff uv.lock   # review before committing

Commit the regenerated lockfile with the toolchain update.

Phase 5 — Update requires-python and classifiers (optional)

If you want to drop 3.11 and standardize on 3.12+:

requires-python = ">=3.12"

And update classifiers accordingly. Otherwise keep >=3.11 and test both 3.11 and 3.12 in CI.

Phase 6 — Update Gitea CI workflows

The .github/workflows/*.yml files reference Python setup steps. Update them to:

  • Use actions/setup-python with python-version: ["3.11", "3.12"] (or your Gitea Actions equivalent)
  • Install via uv sync --all-groups instead of pip install -e .
  • Run uv run ruff check, uv run pyright, uv run pytest

If your Gitea instance uses Gitea Actions, mirror the same matrix. If not, update the workflows to call uv explicitly.

Phase 7 — Packaging scripts review

The utils/ build scripts (build_appimage.py, build_debian.py, build_flatpak.py, build_pypi.py, build_windows.py) and setup/ packaging may pin Python/Qt versions. Check each for:

  • Hardcoded python3 → should target the new runtime
  • qt_version = "6.11" in [tool.novelwriter.build] flatpak → verify against latest Qt6
  • pyqt6>=6.4 lower bound → keep or raise

Phase 8 — Validation

  1. Syntax/compile: uv run python -m py_compile umbraedit/ tests/ utils/
  2. Import smoke: uv run python -c "import umbraedit; umbraedit.main(['--help'])"
  3. Lint: uv run ruff check . and uv run pyright
  4. Tests: uv run pytest (or uv run python run_tests.py)
  5. App launch: uv run python UmbraEdit.py — confirm main window opens
  6. Export formats: exercise DOCX/EPUB/HTML/ODT export paths if sample data exists

Phase 9 — Commit & publish

git add -A
git commit -m "chore: upgrade toolchain to Python 3.12 and latest deps

- Upgrade uv and pin Python 3.12 via .python-version
- Refresh pyproject.toml dependency groups to latest compatible versions
- Regenerate uv.lock
- Update Gitea CI workflows for uv + Python 3.11/3.12 matrix
- Review packaging scripts for hardcoded python/qt versions"
git push origin main

3. Rollback Plan

If anything breaks after the update:

# Restore previous state
git checkout umbraedit/pre-toolchain-update .
# or reset hard to the tag
git reset --hard umbraedit/pre-toolchain-update
git push origin main --force   # only if already pushed and you need to undo

Also keep the old system Python 3.9.6 available (do not remove /usr/bin/python3), and keep the upstream remote pointing at the original novelWriter for reference.


cd /Volumes/1TB_APL_Storage/novelWriter2

# 0. Tag rollback point
git tag umbraedit/pre-toolchain-update
git push origin umbraedit/pre-toolchain-update

# 1. Upgrade uv and pin Python 3.12
uv self upgrade
uv python install 3.12
uv python pin 3.12
uv run python --version

# 2. Create venv and install runtime deps at latest
uv venv --python 3.12
uv pip install "pyqt6>=6.4" "pyenchant>=3.3.0"

# 3. Smoke-test the app
uv run python UmbraEdit.py

# 4. Sync dev toolchains (lint/test/docs)
uv sync --all-groups

# 5. Regenerate lockfile
uv lock --upgrade
git diff uv.lock | head -100

# 6. Validate
uv run python -m py_compile umbraedit/ tests/ utils/
uv run ruff check .
uv run pytest

5. Notes & Risks

  • PyQt6 on Python 3.13: Wheels may lag; if 3.13 is required, verify PyQt6 availability first. 3.12 is the safer target.
  • pyobjc-framework-Cocoa: macOS-only; only install/test on darwin.
  • uv.lock diff: Expect a large diff since the lockfile is stale; review that no unexpected major-version jumps occur (especially PyQt6 6.x → 7.x, which would be breaking).
  • CI: Gitea Actions runners must have uv installed, or the workflows must install it as a step.
  • Application still runs on Python 3.9.6? No — match/case syntax requires 3.10+, and requires-python is >=3.11. The system 3.9.6 must not be used to run UmbraEdit.