Drag fields, get charts
Drop a field on the canvas and smaltbi picks a visual. Change its type, add fields to its axis, legend or values, and format it from the side panel.
Small. Alternative. Insight.
smaltbi is a report designer and viewer. Load CSV, JSON or Parquet files, model them with relationships and SQL measures, drag fields onto a canvas, and publish the result as a static site. Every report runs in its reader's browser, on smaltdb, a fast alternative database for the browser.
This is the sample report for a small coffee and tea shop: about 17,000 sales across customers, products and stores, loaded into smaltdb in your browser. Click a bar or a region to filter the page, double-click a column to drill down, or right-click a country on Customers & stores to drill through.
Drop a field on the canvas and smaltbi picks a visual. Change its type, add fields to its axis, legend or values, and format it from the side panel.
Relationships, measures written as SQL aggregates that build on each other ([Revenue] - [Cost]), calculated columns and drill hierarchies. The model view draws it all as a diagram.
Each chart runs one readable query, joined along your relationships. Open the SQL tab to see it, copy it, or replace it with your own.
Cross-filtering, slicers, report, page and visual filters, drill down and drill-through, tooltips, bookmarks, and the view state in the link.
Portable theme files set colours, palettes, fonts and layout, in light and dark. The default theme is the smalt brand; switching themes never re-runs a query.
smaltdb runs in a Web Worker and keeps data in memory or in the browser's private storage (OPFS). The page fetches only the files a report loads.
A report is one JSON file that diffs well in git. Publishing packs it with the viewer, smaltdb and its data into a folder for any static host. The sample is one such site.
{
"smaltbi": 1,
"name": "Sales",
"data": { "steps": [
{ "import": "data/sales.csv", "table": "sales" },
{ "import": "data/customers.csv", "table": "customers" }
] },
"model": {
"relationships": [
{ "from": "sales.customer_id", "to": "customers.id" }
],
"measures": [
{ "table": "sales", "name": "Revenue",
"sql": "SUM(sales.quantity * sales.unit_price)" }
]
},
"theme": "smalt",
"pages": [ … ]
}
node scripts/publish.mjs report.json out/ in a pipeline.