Real-Time Dashboards

Scorecards, KPIs, charts, and tabular views powered by ClickHouse with drill-down analytics.

Real-Time Dashboards

Dashboards That Tell the Truth

Tuli dashboards reflect the current state of your business — not yesterday's batch export. Powered by ClickHouse, every widget updates in real-time as data changes.

Widget Types

Build dashboards from a rich library of widget types:

  • Scorecard — Single metric with comparison, trend, and target
  • KPI Card — Key metric with sparkline and period comparison
  • Pie Chart — Distribution and composition analysis
  • Bar Chart — Comparisons across categories and time periods
  • Trendline — Time-series data with moving averages
  • Aging Analysis — Bucketed aging for receivables, payables, tickets
  • Tabular — Sortable data grids with inline calculations and totals

P9 Dashboard Definition

Define dashboards declaratively:

@dashboard FinancialOverview
@application Finance
@time-period-filter true

scorecard TotalRevenue {
	label: "Total Revenue"
	value-key: "Total"
	unit: "@company-currency"
	query: "SELECT SUM(Amount) as Total FROM wh_Finance_Invoice WHERE Status = 'Paid' AND IsDeleted = false"

	widget-filter {
		"toYear(CreatedAt)" = @year
	}
}

kpicard OutstandingAR {
	label: "Outstanding AR"
	primary-value-key: "Balance"
	primary-value-format: "currency"
	secondary-value-key: "Count"
	query: "SELECT SUM(Balance) as Balance, COUNT(*) as Count FROM wh_Finance_Receivable WHERE Status = 'Open' AND IsDeleted = false"
}

pie ExpensesByCategory {
	label: "Expenses by Category"
	label-key: "Category"
	value-key: "Total"
	query: "SELECT Category, SUM(Amount) as Total FROM wh_Finance_Expense WHERE IsDeleted = false GROUP BY Category ORDER BY Total DESC LIMIT 8"

	widget-filter {
		"toYear(CreatedAt)" = @year
	}

	group-by {
		key: "Category"
	}
}

bar MonthlyRevenue {
	label: "Revenue by Month"
	x-axis-key: "Month"
	y-axis-key: "Total"
	query: "SELECT formatDateTime(CreatedAt, '%b') as Month, SUM(Amount) as Total FROM wh_Finance_Payment WHERE IsDeleted = false GROUP BY Month ORDER BY toMonth(CreatedAt)"

	widget-filter {
		"toYear(CreatedAt)" = @year
	}

	group-by {
		key: "formatDateTime(CreatedAt, '%b')"
	}
}

aging ARAgeing {
	label: "Receivables Aging"
	tint: "negative"
	query: "SELECT CASE WHEN dateDiff('day', DueDate, today()) <= 30 THEN '0-30 days' WHEN dateDiff('day', DueDate, today()) <= 60 THEN '31-60 days' WHEN dateDiff('day', DueDate, today()) <= 90 THEN '61-90 days' ELSE '90+ days' END AS label, SUM(Balance) AS value FROM wh_Finance_Receivable WHERE Status = 'Open' AND IsDeleted = false GROUP BY label"
}

Interactive Features

  • Click to drill down — Every widget supports click-through to underlying data
  • Filter synchronization — Dashboard-level filters apply to all widgets simultaneously
  • Responsive layout — Widgets reflow for mobile and tablet views
  • Auto-refresh — Configurable refresh intervals from 10 seconds to hourly
  • Full-screen mode — Expand any widget for presentations
  • Export — Download chart images or underlying data as CSV

Ready to Transform Your Business?

See how Tuli ERP can streamline your operations with AI-powered workflows, real-time dashboards, and seamless integration across all your business modules.