LazyReports.jl

LazyReports provides report generation with minimal dependencies; thus, depending on LazyReports should have minimal load-time impact for Julia packages. Reports are a mixture of text and data objects, and are lazy in the sense that they are easy to create and their contents are only rendered when the report is displayed or written to a file. This way, reports can be generated as part of algorithms and workflows with only a small runtime overhead.

The central function of the package is lazyreport. It generates a report object that can be rendered (via show and display) in different MIME types. lazyreport allows for appending content to reports.

Reports are displayed automatically in the REPL (as far as supported by the report objects), in Jupyter and Pluto notebooks, and in Visual Studio Code (when using the Julia extension). Reports can also be written to files using write_lazyreport.

In addition to the types the current Julia display supports, LazyReports also has special support for StatsBase.Histogram (one-dimensional only).

For example:

using LazyReports, StructArrays, StatsBase, Plots

tbl = StructArray(
    col1 = rand(5),
    col2 = [rand(3) for i in 1:5],
    col3 = [:(a[1]), :(a[2]), :(a[3]), :(a[4]), :(a[5])],
    col4 = [fit(Histogram, rand()^3 * 1000 * randn(10^4), nbins = 50) for i in 1:5],
)

rpt = lazyreport(
    "# New report",
    "Table 1:", tbl
)
lazyreport!(rpt, "Figure 1:", stephist(randn(10^3)))
lazyreport!(rpt, "Figure 2:", histogram2d(randn(10^4), randn(10^4), format = :png))

New report

Table 1:

col1 col2 col3 col4
0.608125 [0.844859, 0.00957264, 0.717674] a[1]
-3e+03[[3e+03
0.841563 [0.0740266, 0.746558, 0.490347] a[2]
-420[[380
0.846756 [0.56376, 0.925507, 0.0897114] a[3]
-150[[160
0.373524 [0.679841, 0.165491, 0.45776] a[4]
-0.28[[0.26
0.153635 [0.162394, 0.993343, 0.910946] a[5]
-800[[700

Figure 1:

Figure 2:

The lower-level function LazyReports.pushcontent! can be specialized to control how objects of specific types are added to reports (e.g. by converting them to Markdown, tables or supported content types first).

Lazy tables

lazytable wraps/converts Tables.jl-compatible objects and allows for adding custom column labels.

using IntervalSets

tbldata = (
    a = ClosedInterval.(rand(5), rand(5).+1),
    b = rand(Bool, 5),
    c = ["a", "b", "c", "d", "e"],
)

lazyreport(
    "# Table report",
    lazytable(tbldata, headers = Dict(:a => "Intervals", :b => "Booleans", :c => "Strings"))
)

Table report

Intervals Booleans Strings
0.274482 .. 1.9332 true a
0.502406 .. 1.44132 false b
0.671052 .. 1.98051 true c
0.293712 .. 1.14446 false d
0.26298 .. 1.54385 false e

Rendering Plots

When rendering reports using MIME("text/plain"), e.g. when showing reports on the REPL and when writing reports to ".txt" files, LazyReports will try to convert Plots.jl plots to the Plots.UnicodePlotsBackend. UnicodePlots will be loaded automatically, but the package UnicodePlots must be part of your Julia environment or rendering will fail. Note that converting Plots generated with a different backend (e.g. the default GR backend) to UnicodePlots will not always yield satisfactory results, depending on the type of plot.