Table of Contents

Reports

/reports, in modules/requests/Reports (SCRUM-132, SCRUM-158).

One scope

Who reads which rows is ReportScope alone: ViewAllReports reads everything, ViewDepartmentReports the requests and bookings of the viewer's department (by the department recorded on the request at creation, never the card as it is now), and neither reads nothing. The page, the groups and the export all go through it.

One query, in the database

  • RequestsReport filters through RequestSearch.ApplyAsync (the same builder as every request list, so a report counts what the lists count), plus department, branch and a submission range of local days passed to SQL in UTC.
  • Rows are paged with Skip/Take; groups are counted in SQL by their key (TallyAsync); a month is a comparison of instants, so SQLite runs it too.
  • BookingsReport filters by room, type, state, department and day.

Any value is a column (ReportValues)

One catalog of values serves columns, filters and groupings: the requester's card as it is (u:: employee number, e-mail, line manager) and what the request's form holds (f:: the chosen service's fields and its list details). A form value is read in SQL (jsonb_extract_path_text on PostgreSQL, json_extract on SQLite), so the report stays paged in the database.

Grouping

By month, service, status, department, branch, step («حسب الخطوة»: average wait, late count and how many wait there now, from the route rows) or any value («حسب قيمة»). A grouped report can add up a number per group (Totals), and ReportChart draws the groups above their table.

Views, columns and export

  • A view is saved settings JSON (ReportJson), changed only by its owner, private or shared with every report reader.
  • A viewer's own columns are kept on «تطبيق» (ReportColumnChoice); columns are dragged into order (sort.js) and sorted by tapping a header.
  • /reports/export writes every filtered row (or the groups) to a right-to-left Excel sheet with real dates and numbers (ClosedXML), and records report.exported.
  • The table is the app's own (ReportTable): plain rows, scrolling sideways on a phone.