Developer documentation for the Stats module of the WPResidence real estate CRM. Covers the stats-functions API, Chart.js integration, deferred loading, and scope filtering.
Files
- libs/stats-functions.php — aggregate queries and counters.
- page-templates/wpestate-crm-dashboard_stats.php — dashboard template.
Server-Side KPI Functions
| Function | Returns |
|---|---|
| wpestate_crm_get_lead_stats() | total, by_status, by_source, by_type |
| wpestate_crm_get_enquiry_stats() | Counts keyed by status |
| wpestate_crm_get_deal_stats() | total, value_sum, by_stage, avg_value, won_count, lost_count |
| wpestate_crm_get_tasks_by_priority() | Task counts per priority |
| wpestate_crm_stats_tasks_overdue() | int — overdue task count |
KPI Tiles (Server-Side Render)
The 5 tiles render synchronously in the template using the stats functions above plus helper date math:
- first_day_of_month / first_day_of_prev_month — for “this month vs. previous” deltas.
- monday_this_week / monday_last_week — for weekly activity delta.
- Overdue tasks: conditional red CSS class applied when count > 0.
Charts (Deferred AJAX Render)
All six charts load after first paint via an AJAX call, to keep the page fast on sites with many records:
| Action | Purpose |
|---|---|
| wpestate_crm_get_stats | Returns JSON payload with labels and datasets for all six charts. |
Chart.js 4.4.7 is enqueued conditionally on the Stats page only (check in wpestate-crm.php around lines 59/90). The chart render logic reads wpestate_crm_vars.nonces for the request.
The Six Charts
- Contacts by Lifecycle Stage — doughnut.
- Deals by Pipeline Stage — bar with count + value.
- New Contacts over Time — line, 30-day rolling.
- Activity Volume by Type — bar.
- Deal Win/Loss Ratio — pie.
- Task Completion Rate — bar (% completed vs. total).
Scope Filtering
Every stats function respects wpestate_crm_get_ownership_where(). Admins receive unfiltered queries; agents get WHERE clauses scoped to their user_id and assigned agent ID.
Capabilities
The template is gated by wpestate_dashboard_header_permissions() (login required) and individual functions also respect wpestate_crm_user_can(‘activities’, ‘view’) where applicable.
Customizing Charts
- To add a metric, extend libs/stats-functions.php from a child plugin (do not edit the CRM plugin directly).
- Inject your new dataset into the wpestate_crm_get_stats AJAX response with a priority-20 filter on the response JSON.
- Add a <canvas> element in a child template override of wpestate-crm-dashboard_stats.php and wire it to a Chart.js constructor on DOM ready.
Performance Notes
- Pipeline summary uses a single GROUP BY deal_stage query.
- Contacts-by-lifecycle uses a single GROUP BY lifecycle_stage query.
- Activity volume uses a GROUP BY type with a WHERE created_at >= filter (last 30 days by default).
- For sites with 100K+ rows, consider adding materialized summary tables and a daily cron to refresh them.