Feature: pluggable HTML themes via Jinja2 template inheritance
评估
这个 Issue 还没有评估数据。
描述
Motivation
There is clear user demand for a modernised report UI (see #913, #904, #884). Currently, anyone who wants a different visual style has to override CSS after the fact or maintain a separate fork. pytest-html could instead offer first-class theme support, making it trivial to ship alternative report styles and for the community to contribute new ones.
Proposed design
1. Jinja2 template inheritance with {% extends %}
Factor the current index.jinja2 into a base template and per-theme overrides:
resources/
base.jinja2 # shared HTML skeleton with {% block %} placeholders
classic/
layout.jinja2 # {% extends "base.jinja2" %} — current look
style.css
modern/
layout.jinja2 # {% extends "base.jinja2" %} — card-based dashboard
style.css
Only 4 blocks actually differ between visual styles:
{% block header %}— page title / navbar{% block summary %}— run stats presentation (flat text vs stat cards with percentages){% block filters %}— checkboxes vs toggle switches{% block footer %}— generation info placement
Everything else is shared in base.jinja2: the results table, the <template> for result rows, the media viewer, the JS data container, and the script include.
2. Config option
# pytest.ini / pyproject.toml
[tool.pytest.ini_options]
html_theme = "modern" # default: "classic"
# plugin.py
parser.addini(
"html_theme",
type="string",
default="classic",
help="HTML report theme ('classic' or 'modern').",
)
3. Template loader change
Pass [theme_path, resources_path] to Jinja2's FileSystemLoader so each theme's layout.jinja2 can do {% extends "base.jinja2" %} and the loader resolves base.jinja2 from the parent resources directory. Minimal change to _read_template.
4. Extra template variables
A modern card-based theme benefits from a few additional pre-computed template variables. These are cheap to compute and can be passed unconditionally so all themes have them available:
start_time/end_time— formatted timestamps for the suiteduration_display— human-readable total durationtotal_count— total tests excluding reruns
This is ~15 lines in _generate_report().
Benefits
- Backward compatible —
classicis the default; no one's custom CSS breaks - Extensible — new themes are just a directory with
layout.jinja2+style.css - Low risk — the JS logic, data model, hooks, and Python backend are untouched
- Community-friendly — lowers the bar for contributing visual improvements
What this does NOT change
- No new features or hooks — purely a presentation-layer refactor
- No change to the default appearance (classic remains default)
- No JS modifications required
- 主要语言
- Python
- 星标
- 779
- 派生
- 259
- PR 合并指标
- 30 天内没有已合并 PR
环境准备
这个项目没有提供开发容器、Dockerfile 或贡献指南,环境需要你自己搭建:先看它的 README,通用步骤见我们的新手贡献指南。
从这里开始
- 先读完整个 Issue,再读项目的贡献指南。
- 在 Issue 下留言说明你要接手 —— 这能避免两个人做同样的事。
- Fork 仓库,在一个分支上完成修改。
- 提交 Pull Request,并在描述里引用这个 Issue 编号。
pytest-dev/pytest-html 的其他 Issue
-
难度 3/5 1-2 天 新手友好度 68/100
pytest-dev/pytest-html#1077 ·
-
难度 4/5 3-5 天 新手友好度 42/100
pytest-dev/pytest-html#1039 ·
-
难度 3/5 1-2 天 新手友好度 55/100
pytest-dev/pytest-html#1027 ·
-
pytest-html does not escape HTML in testId (v4.2.0)可能已有人在做 @golikovichev 于 120 天前认领。 未关闭
难度 3/5 1-2 天 新手友好度 55/100
pytest-dev/pytest-html#1024 ·
-
难度 3/5 1-2 天 新手友好度 48/100
pytest-dev/pytest-html#1010 ·
查看 pytest-dev/pytest-html 的全部 Issue
相似的 Issue
-
难度 2/5 1-3 小时 新手友好度 85/100
维护者通常 1 天内回复
-
SR_SECURITY_DESCRIPTOR.fromString drops the SACL when no DACL is present可能已有人在做 @paul7436 今天认领。 未关闭
难度 2/5 1-3 小时 新手友好度 88/100
维护者通常 2 天内回复
-
难度 2/5 1-3 小时 新手友好度 85/100
equinor/fmu-sumo-uploader#302 ·
维护者通常 1 天内回复
-
难度 2/5 1-3 小时 新手友好度 75/100
modelscope/evalscope#1821 ·
维护者通常 1 天内回复
-
Sanity on ansible-core devel fails: ignore-2.23.txt references the removed import-3.9 test可能已有人在做 @yurnov 今天认领。 未关闭needs_triage
难度 1/5 1 小时以内 新手友好度 91/100
ansible-collections/kubernetes.core#1275 ·
维护者通常 1 天内回复