Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
Show all changes
39 commits
Select commit Hold shift + click to select a range
e05588d
Update default.html to use Classless.css and improve styling variables
darenr Mar 7, 2026
704aa18
migrate to classless
darenr Mar 9, 2026
8d58623
migrate to classless, fix up datatable issues
darenr Mar 11, 2026
a106fbf
fix logo image styles
darenr Mar 11, 2026
eb0092a
styling changes
darenr Mar 12, 2026
42e5f8c
fix up fonts of plots
darenr Mar 12, 2026
48efa0a
fix issue with text indents being treated in rc.Text/Markdown as code
darenr Mar 13, 2026
b3ab56f
fix font size in logo
darenr Mar 13, 2026
200741b
Refactor CSS styles in default.html and update font size in report_cr…
darenr Mar 13, 2026
fafade3
Refactor code structure for improved readability and maintainability
darenr Mar 13, 2026
63725da
remove test code
darenr Mar 13, 2026
e0bc2e0
Update Markdown class docstring to clarify text formatting and features
darenr Mar 13, 2026
ac756f9
Implement feature X to enhance user experience and fix bug Y in module Z
darenr Mar 13, 2026
fb55ccf
begin v2
darenr Mar 22, 2026
8ef7b89
perf: compile SQL formatting regex patterns at class level
darenr Mar 19, 2026
83e5686
pre-release v2
darenr Mar 22, 2026
26801c4
Add optional footer support to Markdown section and update styles
darenr Mar 22, 2026
59dd1f6
fix styling inconsistencies with data tables
darenr Mar 22, 2026
edd221f
add rc.Code that supports outputting other languages including html (…
darenr Mar 23, 2026
55afa04
Refactor Code class documentation and remove YAML support
darenr Mar 23, 2026
ca1c0f5
Add support for additional programming languages and enhance Code com…
darenr Mar 23, 2026
37e3ea7
Enhance documentation for code components and improve index formatting
darenr Mar 23, 2026
b88e898
feat: replace footer with sublabel in Markdown component
darenr Mar 23, 2026
e93db86
Refactor code structure for improved readability and maintainability
darenr Mar 23, 2026
705ae45
add contrast color and better support for accent color throughout report
darenr Mar 24, 2026
8ffbde5
perf: optimize error keyword matching in create_color_value_sensitive…
darenr Mar 25, 2026
3059a8a
sync up with main
darenr Mar 25, 2026
5c3c4c6
Fix active tab button styles: correct color declaration and add bold …
darenr Mar 25, 2026
61ad1ea
Refactor tab button styles in default.html
darenr Mar 26, 2026
9797b6a
Refactor image block class and enhance admonition styles
darenr Mar 26, 2026
141a5a3
Implement feature X to enhance user experience and optimize performance
darenr Mar 26, 2026
3b4b402
Refactor logging levels in report_creator
darenr Mar 26, 2026
4fb1136
update changelog
darenr Mar 26, 2026
062f874
fix: downgrade version to 1.2.0 and update language inference
darenr Mar 27, 2026
00493d0
Remove unnecessary language scripts from default.html to optimize loa…
darenr Mar 27, 2026
67d7da3
Add Prolog and Rust language support to syntax highlighting; clean up…
darenr Mar 27, 2026
e8fab6b
Refactor EventMetric class for improved clarity and functionality
darenr Mar 28, 2026
28bb521
prep for 1.2 release
darenr Mar 30, 2026
3b1a231
Merge branch 'feature-switch-water-to-classless'
darenr Mar 30, 2026
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
2 changes: 1 addition & 1 deletion .gitignore
Original file line number Diff line number Diff line change
Expand Up @@ -166,4 +166,4 @@ aa.htm*
htmlcov/
output.prof
infographic.html
.last_run
.last_run
20 changes: 18 additions & 2 deletions CHANGELOG.md
Original file line number Diff line number Diff line change
Expand Up @@ -2,10 +2,26 @@

All notable changes to this project will be documented in this file.

## 1.2.0 (April 2026)

- No breaking changes.
- Switch CSS from water.css to classless.css, to prevent interference between styling in libraries
- Updates DataTable javascript library version
- Indented text in rc.Text or rc.Markdown will *not* be treated as code blocks, use fenced blocks explicitely
- Added `rc.Code()`, added language aliases (txt -> plaintext, js -> javascript)
- Added sublabel option for the `rc.Text()` and `rc.Markdown()` components to allow a styled footer.
- Respect `accent_color` throughout the report by setting --secondary css variable, when an accent color that has a lightness that flips the color of text the text will be colored correctly (not using css `contrast-color` which doesn't work on Chrome)
- The `rc.Markdown()` component now supports fenced directives, adminitions include: `attention`, `caution`, `danger`, `error`, `hint`, `important`, `note`, `tip`, and `warning` see example below. Use either Fenced or RST syntax, both work.

```{danger}
Danger, Will Robinson! Danger!
```

## 1.1.5 (March 2026)

- Refresh dependencies
- Minor styling fixes
- Put blocks of CSS into layers (framework, library, app) with ordering
- Minor sytyling changes
- Performance improvements in html generation and rendering

## 1.1.4 (February 4, 2026)

Expand Down
19 changes: 18 additions & 1 deletion Makefile
Original file line number Diff line number Diff line change
@@ -1,8 +1,10 @@
all: setup examples
.PHONY: clean examples

SENTINEL = .last_run
TIMEOUT = 5 # minutes

setup:
actual_setup:
@echo "Setting up environment..."
@python3 -m pip install -q --upgrade pip
@python3 -m pip install -qr requirements.txt -U
Expand All @@ -11,6 +13,17 @@ setup:
@echo "Installing/updating dev tools..."
@python3 -m pip install -q ruff twine ghapi -U

setup:
@# Check if the sentinel exists and was modified less than 5 minutes ago, \
@# speed up development by skipping environment setup if it was recently done
@if [ -f $(SENTINEL) ] && [ `find $(SENTINEL) -mmin -$(TIMEOUT)` ]; then \
echo "Skipped environment setup: Run less than $(TIMEOUT) minutes ago."; \
else \
$(MAKE) actual_setup; \
touch $(SENTINEL); \
fi


examples: setup
@for file in $(wildcard examples/*.py); do \
PYTHONPATH=. python $$file; \
Expand Down Expand Up @@ -39,6 +52,10 @@ format:
@ruff check report_creator
@python scripts/utils/ruffen-docs.py README.md

sync:
@git fetch origin
@git rebase origin/main

release: setup clean
@find ./ -name '*.pyc' -exec rm -f {} \;
@find ./ -name 'Thumbs.db' -exec rm -f {} \;
Expand Down
34 changes: 24 additions & 10 deletions README.md
Original file line number Diff line number Diff line change
Expand Up @@ -3,7 +3,6 @@
[![License](https://img.shields.io/badge/license-MIT-blue.svg?style=for-the-badge)](https://www.apache.org/licenses/LICENSE-2.0)
[![PyPI Version](https://img.shields.io/pypi/v/report_creator.svg?style=for-the-badge&color=blue)](https://pypi.org/project/report_creator)
[![Python Versions](https://img.shields.io/pypi/pyversions/report_creator.svg?logo=python&logoColor=white&style=for-the-badge)](https://pypi.org/project/report_creator)
[![Python Stats](https://img.shields.io/pypi/dw/report_creator?style=for-the-badge)](https://pypi.org/project/report_creator)

[GitHub](https://github.com/darenr/report_creator) |
[PyPI](https://pypi.org/project/report_creator/) |
Expand All @@ -18,21 +17,35 @@ either the horizontal (`rc.Group()`) or Vertical (`rc.Block()`) direction.
Talk to this repo using [DeepWiki Report Creator](https://deepwiki.com/darenr/report_creator)

Use the documentation in Cursor, Windsurf, Claude Desktop or another MCP Client via the [Context7 MCP](https://context7.com/darenr/report_creator) for example

```plaintext
Create an html report on this dataframe, use context7
```

## Features

- [x] Good pandas/dataframe/table support
- [x] Look modern
- [x] Allows markdown as input for text blocks
- [x] Allows html as input
- [x] Components for things like metrics ("Accuracy: 87%") from a key & value
- [x] Support for plotting figures, interactive `plotly` and `matplotlib`
- [x] Images (styled by the library) with an option to fetch at report build time (no fetch on render)
- [x] Supports faithful extended markdown support (emojis, mermaid etc)
- [x] `json`/`yaml`/`python`/`java`/`prolog`/`plaintext` code blocks with color syntax highlighting
### Data & Visualization

- **Deep Pandas Integration**: Native support for DataFrames in `Table`, `DataTable` (searcheable/sortable), and `Metric` components.
- **Interactive Plotting**: Full support for `Plotly` figures with a custom "RC" theme for professional-looking charts by default.
- **Matplotlib & Seaborn**: Automatic detection and rendering of `Matplotlib` and `Seaborn` objects, with consistent styling using a context manager.
- **Specialized Charts**: Built-in components for `Radar` charts, `Bar`, `Line`, `Pie`, `Scatter`, `Box`, and `Histogram`.
- **Advanced Metrics**: `Metric` and `MetricGroup` for KPI displays, including `EventMetric` for time-series frequency analysis.

### Content & Layout

- **Rich Layout System**: Flexible report structuring using `rc.Block()` (vertical) and `rc.Group()` (horizontal) stacks.
- **Modern UI Components**: Interactive elements like `Accordion`/`Collapse` sections and `Select` tabbed interfaces.
- **Superior Markdown**: Full GitHub Flavored Markdown (GFM) support, including Emojis, Math (LaTeX), and RST directives.
- **Diagrams as Code**: Native `Mermaid.js` support for flowcharts, sequence diagrams, and more, with built-in pan and zoom.

### Technical Capabilities

- **Syntax Highlighting**: Code blocks with support for multiple languages including `Sql`, `Python`, `Yaml`, and `Json`.
- **SQL Prettifier**: Heuristic formatting for SQL queries to improve readability in reports.
- **Smart Media Handling**: Images can be local, remote (fetched at build time), or Base64 encoded, with automatic styling.
- **Self-Contained Output**: Generates standalone HTML files that bundle only the required JavaScript dependencies (Plotly, DataTables, etc.).
- **Deterministic Styling**: Automatic, repeatable color generation for headings and labels to ensure visual consistency.

## Example

Expand All @@ -43,6 +56,7 @@ with rc.ReportCreator(
title="My Report",
description="My Report Description",
footer="My Report Footer",
accent_color="red"
) as report:
view = rc.Block(
rc.Text(
Expand Down
8 changes: 4 additions & 4 deletions coverage_report.md
Original file line number Diff line number Diff line change
@@ -1,8 +1,8 @@
| Name | Stmts | Miss | Branch | BrPart | Cover |
|----------------------------------- | -------: | -------: | -------: | -------: | ------: |
| report\_creator/base.py | 8 | 1 | 0 | 0 | 88% |
| report\_creator/charts.py | 231 | 11 | 96 | 13 | 93% |
| report\_creator/report\_creator.py | 673 | 177 | 146 | 23 | 72% |
| report\_creator/charts.py | 233 | 11 | 96 | 13 | 93% |
| report\_creator/report\_creator.py | 721 | 171 | 164 | 26 | 74% |
| report\_creator/theming.py | 5 | 0 | 0 | 0 | 100% |
| report\_creator/utilities.py | 230 | 10 | 58 | 5 | 95% |
| **TOTAL** | **1147** | **199** | **300** | **41** | **81%** |
| report\_creator/utilities.py | 285 | 13 | 88 | 9 | 94% |
| **TOTAL** | **1252** | **196** | **348** | **48** | **83%** |
20 changes: 17 additions & 3 deletions docs/source/getting_started.rst
Original file line number Diff line number Diff line change
Expand Up @@ -105,13 +105,27 @@ Most components will accept a label, which is a string that may contain Markdown
Code
----

There are components for ``rc.Yaml()``, ``rc.Json()``, ``rc.Python()``, ``rc.Prolog()``, ```rc.Java()``, ``rc.Shell()``, and ``rc.Sql()``, each
will format and render with color syntax highlighting. Plain text can also be styled as code with ``rc.Plaintext()``, although this
has limited use, it can be used to show code that is not in a common language.
There are components for several specific languages where the inout data structure will be rendered, for example ``rc.Yaml()`` and ``rc.Json()``.
For languages like ``rc.Python()``, ``rc.Prolog()``, ```rc.Java()``, ``rc.Shell()``, and ``rc.Sql()``, each
will format and render with color syntax highlighting - you can specify the code theme using ``code_theme`` in the ReportCreator constructor.
Plain text can also be styled as code with ``rc.Plaintext()``, note this is different to ``rc.Text()``. The ``rc.Code()``
component is a more generic code component that takes a ``language`` parameter, the language will be used for syntax highlighting, and must be one
of the supported languages or their aliases. The supported languages are displayed if you specify an unsupported language, and the aliases are
listed in the code. Note that ``rc.Code()`` component takes in a string of code, and the language, while the specific language components
like ``rc.Python()`` take in the code and infer the language from the component type. This is a design choice to make the specific language
components more convenient to use, and the ``rc.Code()`` component more flexible. A concrete example is rc.Code with a markdown string
(and language="markdown") which will format and syntax highlight the markdown properly, while if you use rc.Markdown with a code string
it will render the code as markdown text, not as code. The same is true for Json, Yaml, HTML and Plaintext components.

.. image:: images/code.png
:alt: rc.Java()

Notebook Compatibility
----------------------

The ``rc.Widget()`` component can be used to include any python object that implements the ``_repr_html_()`` method, this is used by Jupyter notebooks to render objects, so for example you can include a matplotlib figure in your report with this component.


Images
------

Expand Down
Binary file modified docs/source/images/code.png
Loading
Sorry, something went wrong. Reload?
Sorry, we cannot display this file.
Sorry, this file is invalid so it cannot be displayed.
4 changes: 2 additions & 2 deletions docs/source/index.rst
Original file line number Diff line number Diff line change
Expand Up @@ -26,9 +26,9 @@ Overview
* **Versatile:** Viewable in any web browser and can be easily printed to PDF.
* **Comprehensive:** Supports a wide array of components including:

* Text and code blocks
* Text and Code blocks
* Images (local, URLs, or base64)
* Data visualizations (powered by Plotly Express)
* Data visualizations/Charts (powered by Plotly Express)
* Tables (static or interactive)
* Diagrams (using Mermaid.js)
* **Customizable:** Markdown support within components or as labels/descriptions for other components.
Expand Down
File renamed without changes.
24 changes: 9 additions & 15 deletions examples/example.txt
Original file line number Diff line number Diff line change
@@ -1,15 +1,9 @@
Alice was beginning to get very tired of sitting by her sister on the bank, and of having nothing to do: once
or twice she had peeped into the book her sister was reading, but it had no pictures or conversations in it,
*“and what is the use of a book,”* thought Alice *“without pictures or conversations?”*

So she was considering in her own mind (as well as she could, for the hot day made her feel very sleepy and
stupid), whether the pleasure of making a daisy-chain would be worth the trouble of getting up and picking
the daisies, when suddenly a White Rabbit with pink eyes ran close by her.

There was nothing so very remarkable in that; nor did Alice think it so very much out of the way to hear the
Rabbit say to itself, *“Oh dear! Oh dear! I shall be late!”* (when she thought it over afterwards, it occurred
to her that she ought to have wondered at this, but at the time it all seemed quite natural); but when the
Rabbit actually took a watch out of its waistcoat-pocket, and looked at it, and then hurried on, Alice
started to her feet, for it flashed across her mind that she had never before seen a rabbit with either
a waistcoat-pocket, or a watch to take out of it, and burning with curiosity, she ran across the field
after it, and fortunately was just in time to see it pop down a large rabbit-hole under the hedge.
... Look again at that dot. That's here. That's home. That's us. On it everyone you love, everyone you know, everyone you ever heard of, every human being who ever was, lived out their lives. The aggregate of our joy and suffering, thousands of confident religions, ideologies, and economic doctrines, every hunter and forager, every hero and coward, every creator and destroyer of civilization, every king and peasant, every young couple in love, every mother and father, hopeful child, inventor and explorer, every teacher of morals, every corrupt politician, every "superstar," every "supreme leader," every saint and sinner in the history of our species lived there - on a mote of dust suspended in a sunbeam.

The Earth is a very small stage in a vast cosmic arena. Think of the rivers of blood spilled by all those generals and emperors, so that, in glory and triumph, they could become the momentary masters of a fraction of a dot. Think of the endless cruelties visited by the inhabitants of one corner of this pixel on the scarcely distinguishable inhabitants of some other corner, how frequent their misunderstandings, how eager they are to kill one another, how fervent their hatreds. Our posturings, our imagined self-importance, the delusion that we have some privileged position in the Universe, are challenged by this point of pale light.

Our planet is a lonely speck in the great enveloping cosmic dark. In our obscurity, in all this vastness, there is no hint that help will come from elsewhere to save us from ourselves.

The Earth is the only world known so far to harbor life. There is nowhere else, at least in the near future, to which our species could migrate. Visit, yes. Settle, not yet. Like it or not, for the moment the Earth is where we make our stand.

It has been said that astronomy is a humbling and character building experience. There is perhaps no better demonstration of the folly of human conceits than this distant image of our tiny world. To me, it underscores our responsibility to deal more kindly with one another, and to preserve and cherish the pale blue dot, the only home we've ever known.
41 changes: 23 additions & 18 deletions examples/kitchen_sink.py
Original file line number Diff line number Diff line change
Expand Up @@ -11,9 +11,14 @@

if __name__ == "__main__":
# set up of example text, plots and dataframes
df1 = pd.DataFrame(columns=["Name", "Age"])
df1.Name = ["Lizzie", "Julie", "Andrea"]
df1.Age = [24, 18, 22]
df1 = pd.DataFrame(
{
"Name": ["Alice", "Bob", "Eva"],
"Age": [25, 30, 35],
"City": ["New York", "Los Angeles", "Chicago"],
"Salary": [70000, 85000, 95000],
}
)
df2 = px.data.stocks()

with open(__file__) as f:
Expand All @@ -30,11 +35,11 @@
with rc.ReportCreator(
title="Kitchen Sink",
description="**All** the *things*",
footer=f"Made with `report_creator` (v{rc.__version__}), `pip install report-creator` :red_heart:",
footer=f"Made with [report_creator](https://github.com/darenr/report_creator) (v{rc.__version__}), `pip install report-creator` :cat_face:",
) as report:
view = rc.Block(
rc.Collapse(
rc.Python(example_python, label="kitchen_sink.py"),
rc.Code(example_python, label="kitchen_sink.py"),
label="Code (kitchen_sink.py) to create this report",
),
rc.Group(
Expand Down Expand Up @@ -83,20 +88,18 @@
),
rc.Group(
rc.EventMetric(
pd.read_csv("examples/logs.csv"),
pd.read_csv("examples/example-public-logs.csv"),
condition="status == 200",
color="black",
date="time",
color="green",
frequency="B",
heading="Successful Requests",
),
rc.EventMetric(
pd.read_csv("examples/logs.csv"),
pd.read_csv("examples/example-public-logs.csv"),
condition="status == 404",
color="black",
date="time",
frequency="B",
heading="Not Found Requests",
heading="Not Found (404) Requests",
),
label="Log File Metrics",
),
Expand Down Expand Up @@ -141,7 +144,9 @@
),
rc.Text(
example_text,
label="Alice’s Adventures in Wonderland (Text)",
label="Pale Blue Dot (1994) by Carl Sagan",
sublabel="For all the software engineers that have been inspired by Carl Sagan's words to pursue a career in computer science and engineering, many of which I consider to be friends and colleagues. This is for you.",
bordered=True,
),
rc.Group(
rc.Java(
Expand Down Expand Up @@ -209,27 +214,27 @@
px.data.gapminder().query("year == 2002").query("continent == 'Europe'"),
values="pop",
names="country",
label="rc.Pie Chart - 2002 Population of European continent",
label="2002 Population of European continent",
),
rc.Pie(
px.data.gapminder().query("year == 2002").query("continent == 'Americas'"),
values="pop",
names="country",
label="rc.Pie Chart - 2002 Population of American continent",
label="2002 Population of American continent",
),
),
rc.Group(
rc.Histogram(
px.data.tips(),
x="total_bill",
dimension="sex",
label="rc.Histogram() Chart of Total Bill",
label="Total Bill by Sex",
),
rc.Box(
px.data.tips(),
y="total_bill",
dimension="day",
label="rc.Box() Chart of Total Bill by Day Dimension",
label="Total Bill by Day of Week",
),
),
rc.Select(
Expand All @@ -239,15 +244,15 @@
x="nation",
y="count",
dimension="medal",
label="Bar Chart - Olympic Medals",
label="Olympic Medals",
),
rc.Scatter(
df=px.data.iris(),
x="sepal_width",
y="sepal_length",
dimension="species",
marginal="histogram",
label="Scatter Plot - Iris",
label="Iris Scatter Plot with Marginal Histograms",
),
],
label="Tabbed Plots",
Expand Down
Loading
Loading