@ministryofjustice/hmpps-digital-prison-reporting-frontend 4.28.8 → 4.29.1

This diff represents the content of publicly available package versions that have been released to one of the supported registries. The information contained in this diff is provided for informational purposes only and reflects changes between package versions as they appear in their respective public registries.
Files changed (197) hide show
  1. package/dpr/all.js +6 -8
  2. package/dpr/all.js.map +3 -3
  3. package/dpr/all.scss +296 -414
  4. package/dpr/all.ts +6 -11
  5. package/dpr/components/_catalogue/catalogue-list/utils.test.ts +1 -1
  6. package/dpr/components/_charts/chart/ChartTimeseries.js +3 -2
  7. package/dpr/components/_charts/chart/ChartTimeseries.js.map +2 -2
  8. package/dpr/components/_charts/chart/ChartTimeseries.ts +4 -2
  9. package/dpr/components/_charts/chart/clientClass.js +1 -0
  10. package/dpr/components/_charts/chart/clientClass.js.map +2 -2
  11. package/dpr/components/_charts/chart/clientClass.ts +1 -0
  12. package/dpr/components/_reports/{report-actions → report-heading/report-actions}/actionsTemplate.js.map +1 -1
  13. package/dpr/components/_reports/{report-actions → report-heading/report-actions}/clientClass.js +1 -1
  14. package/dpr/components/_reports/report-heading/report-actions/clientClass.js.map +7 -0
  15. package/dpr/components/_reports/{report-actions → report-heading/report-actions}/clientClass.ts +1 -1
  16. package/dpr/components/_reports/report-heading/report-actions/types.d.js.map +7 -0
  17. package/dpr/components/_reports/{report-actions → report-heading/report-actions}/types.d.ts +1 -1
  18. package/dpr/components/_reports/{report-actions → report-heading/report-actions}/utils.js.map +1 -1
  19. package/dpr/components/_reports/{report-actions → report-heading/report-actions}/utils.test.ts +2 -2
  20. package/dpr/components/_reports/{report-columns-form → report-heading/report-columns/report-columns-form}/clientClass.js +1 -3
  21. package/dpr/components/_reports/report-heading/report-columns/report-columns-form/clientClass.js.map +7 -0
  22. package/dpr/components/_reports/{report-columns-form → report-heading/report-columns/report-columns-form}/clientClass.ts +1 -3
  23. package/dpr/components/_reports/{report-columns-form → report-heading/report-columns/report-columns-form}/types.d.js.map +1 -1
  24. package/dpr/components/_reports/{report-columns-form → report-heading/report-columns/report-columns-form}/utils.js +1 -1
  25. package/dpr/components/_reports/report-heading/report-columns/report-columns-form/utils.js.map +7 -0
  26. package/dpr/components/_reports/{report-columns-form → report-heading/report-columns/report-columns-form}/utils.ts +2 -2
  27. package/dpr/components/_reports/{report-columns → report-heading/report-columns}/view.njk +1 -1
  28. package/dpr/components/_reports/{report-download-message → report-heading/report-download-message}/clientClass.js +1 -1
  29. package/dpr/components/_reports/report-heading/report-download-message/clientClass.js.map +7 -0
  30. package/dpr/components/_reports/{report-download-message → report-heading/report-download-message}/clientClass.ts +1 -1
  31. package/dpr/components/_reports/{report-filters → report-heading/report-filters}/view.njk +1 -1
  32. package/dpr/components/_reports/report-heading/view.njk +4 -4
  33. package/dpr/components/_reports/report-page/report-print-message/view.njk +10 -0
  34. package/dpr/components/_reports/report-page/report-template/report-no-data-message/styles.scss +8 -0
  35. package/dpr/components/_reports/report-page/report-template/report-no-data-message/view.njk +11 -0
  36. package/dpr/components/_reports/{report-pagination → report-page/report-template/report-pagination}/clientClass.js +1 -1
  37. package/dpr/components/_reports/report-page/report-template/report-pagination/clientClass.js.map +7 -0
  38. package/dpr/components/_reports/{report-pagination → report-page/report-template/report-pagination}/clientClass.ts +1 -1
  39. package/dpr/components/_reports/{report-pagination → report-page/report-template/report-pagination}/types.d.js.map +1 -1
  40. package/dpr/components/_reports/{report-pagination → report-page/report-template/report-pagination}/utils.js.map +1 -1
  41. package/dpr/components/_reports/report-page/report-template/report-section/parent-child-template/styles.scss +88 -0
  42. package/dpr/components/_reports/report-page/report-template/report-section/parent-child-template/view.njk +29 -0
  43. package/dpr/components/_reports/{report-data-table → report-page/report-template/report-section/report-data-table}/clientClass.js +17 -10
  44. package/dpr/components/_reports/report-page/report-template/report-section/report-data-table/clientClass.js.map +7 -0
  45. package/dpr/components/_reports/{report-data-table → report-page/report-template/report-section/report-data-table}/clientClass.ts +20 -10
  46. package/dpr/components/_reports/{report-data-table → report-page/report-template/report-section/report-data-table}/style.scss +35 -185
  47. package/dpr/components/_reports/report-page/report-template/report-section/report-data-table/types.d.js.map +7 -0
  48. package/dpr/components/_reports/{report-data-table → report-page/report-template/report-section/report-data-table}/types.d.ts +2 -2
  49. package/dpr/components/_reports/report-page/report-template/report-section/report-data-table/view.njk +27 -0
  50. package/dpr/components/_reports/report-page/report-template/report-section/styles.scss +33 -0
  51. package/dpr/components/_reports/report-page/report-template/report-section/view.njk +58 -0
  52. package/dpr/components/_reports/{report-summary-table → report-page/report-template/report-summary-table}/styles.scss +21 -4
  53. package/dpr/components/_reports/{report-totals → report-page/report-template/report-totals}/utils.js.map +1 -1
  54. package/dpr/components/_reports/report-page/report-template/styles.scss +5 -0
  55. package/dpr/components/_reports/report-page/report-template/template-config.js +66 -0
  56. package/dpr/components/_reports/report-page/report-template/template-config.js.map +7 -0
  57. package/dpr/components/_reports/report-page/report-template/template-config.ts +45 -0
  58. package/dpr/components/_reports/report-page/report-template/utils.js +82 -0
  59. package/dpr/components/_reports/report-page/report-template/utils.js.map +7 -0
  60. package/dpr/components/_reports/report-page/report-template/utils.ts +100 -0
  61. package/dpr/components/_reports/report-page/report-template/view.njk +61 -0
  62. package/dpr/components/_reports/{report-wrapper → report-page}/styles.scss +7 -5
  63. package/dpr/components/_reports/report-page/view.njk +26 -0
  64. package/dpr/components/card-group/view.njk +0 -4
  65. package/dpr/components/report-list/utils.js +11 -3
  66. package/dpr/components/report-list/utils.js.map +2 -2
  67. package/dpr/components/report-list/utils.ts +11 -1
  68. package/dpr/components/report-list/view.njk +2 -2
  69. package/dpr/components/show-more/style.scss +3 -4
  70. package/dpr/data/reportingClient.js.map +2 -2
  71. package/dpr/data/reportingClient.ts +4 -4
  72. package/dpr/routes/journeys/view-report/async/dashboard/utils.js +1 -1
  73. package/dpr/routes/journeys/view-report/async/dashboard/utils.js.map +1 -1
  74. package/dpr/routes/journeys/view-report/async/dashboard/utils.ts +1 -1
  75. package/dpr/routes/journeys/view-report/async/report/controller.js.map +2 -2
  76. package/dpr/routes/journeys/view-report/async/report/controller.ts +0 -1
  77. package/dpr/routes/journeys/view-report/async/report/report-variants.cy.js +207 -56
  78. package/dpr/routes/journeys/view-report/async/report/report-variants.cy.js.map +2 -2
  79. package/dpr/routes/journeys/view-report/async/report/report-variants.cy.ts +333 -64
  80. package/dpr/routes/journeys/view-report/async/report/utils.js +9 -17
  81. package/dpr/routes/journeys/view-report/async/report/utils.js.map +3 -3
  82. package/dpr/routes/journeys/view-report/async/report/utils.ts +12 -22
  83. package/dpr/routes/journeys/view-report/report.njk +2 -2
  84. package/dpr/routes/journeys/view-report/sync/dashboard/utils.js +1 -1
  85. package/dpr/routes/journeys/view-report/sync/dashboard/utils.js.map +1 -1
  86. package/dpr/routes/journeys/view-report/sync/dashboard/utils.ts +1 -1
  87. package/dpr/routes/journeys/view-report/sync/report/utils.js +38 -11
  88. package/dpr/routes/journeys/view-report/sync/report/utils.js.map +3 -3
  89. package/dpr/routes/journeys/view-report/sync/report/utils.ts +39 -14
  90. package/dpr/routes/journeys/view-report/utils.js +1 -1
  91. package/dpr/routes/journeys/view-report/utils.js.map +1 -1
  92. package/dpr/routes/journeys/view-report/utils.ts +1 -1
  93. package/dpr/services/reportingService.js.map +2 -2
  94. package/dpr/services/reportingService.ts +2 -2
  95. package/dpr/types/ReportQuery.js +1 -1
  96. package/dpr/types/ReportQuery.js.map +1 -1
  97. package/dpr/types/ReportQuery.ts +1 -1
  98. package/dpr/types/UserReports.js.map +1 -1
  99. package/dpr/types/UserReports.ts +3 -3
  100. package/dpr/utils/TemplateBuilder/ParentChildDataBuilder/ParentChildDataBuilder.js +193 -0
  101. package/dpr/utils/TemplateBuilder/ParentChildDataBuilder/ParentChildDataBuilder.js.map +7 -0
  102. package/dpr/utils/TemplateBuilder/ParentChildDataBuilder/ParentChildDataBuilder.ts +203 -0
  103. package/dpr/utils/TemplateBuilder/ParentChildDataBuilder/types.d.js.map +7 -0
  104. package/dpr/utils/TemplateBuilder/ParentChildDataBuilder/types.d.ts +36 -0
  105. package/dpr/utils/TemplateBuilder/ReportBuilder/ReportBuilder.js +114 -0
  106. package/dpr/utils/TemplateBuilder/ReportBuilder/ReportBuilder.js.map +7 -0
  107. package/dpr/utils/TemplateBuilder/ReportBuilder/ReportBuilder.ts +117 -0
  108. package/dpr/utils/TemplateBuilder/ReportBuilder/types.d.js.map +7 -0
  109. package/dpr/utils/TemplateBuilder/ReportBuilder/types.d.ts +6 -0
  110. package/dpr/utils/TemplateBuilder/SectionedDataHelper/SectionedDataHelper.js +202 -0
  111. package/dpr/utils/TemplateBuilder/SectionedDataHelper/SectionedDataHelper.js.map +7 -0
  112. package/dpr/utils/TemplateBuilder/SectionedDataHelper/SectionedDataHelper.ts +246 -0
  113. package/dpr/utils/TemplateBuilder/SectionedDataHelper/types.js +17 -0
  114. package/dpr/utils/TemplateBuilder/SectionedDataHelper/types.js.map +7 -0
  115. package/dpr/utils/TemplateBuilder/SectionedDataHelper/types.ts +41 -0
  116. package/dpr/utils/{CollatedSummaryBuilder/CollatedSummaryBuilder.js → TemplateBuilder/SummaryDataHelper/SummaryDataHelper.js} +6 -8
  117. package/dpr/utils/TemplateBuilder/SummaryDataHelper/SummaryDataHelper.js.map +7 -0
  118. package/dpr/utils/{CollatedSummaryBuilder/CollatedSummaryBuilder.test.ts → TemplateBuilder/SummaryDataHelper/SummaryDataHelper.test.ts} +4 -4
  119. package/dpr/utils/{CollatedSummaryBuilder/CollatedSummaryBuilder.ts → TemplateBuilder/SummaryDataHelper/SummaryDataHelper.ts} +6 -9
  120. package/dpr/utils/TemplateBuilder/TemplateBuilder.js +74 -0
  121. package/dpr/utils/TemplateBuilder/TemplateBuilder.js.map +7 -0
  122. package/dpr/utils/TemplateBuilder/TemplateBuilder.ts +68 -0
  123. package/dpr/utils/definitionUtils.js +22 -2
  124. package/dpr/utils/definitionUtils.js.map +2 -2
  125. package/dpr/utils/definitionUtils.ts +26 -1
  126. package/package.json +1 -1
  127. package/dpr/DprLoadingHelper.js +0 -51
  128. package/dpr/DprLoadingHelper.js.map +0 -7
  129. package/dpr/DprLoadingHelper.ts +0 -27
  130. package/dpr/components/_reports/report/view.njk +0 -40
  131. package/dpr/components/_reports/report-actions/clientClass.js.map +0 -7
  132. package/dpr/components/_reports/report-actions/types.d.js.map +0 -7
  133. package/dpr/components/_reports/report-columns-form/clientClass.js.map +0 -7
  134. package/dpr/components/_reports/report-columns-form/utils.js.map +0 -7
  135. package/dpr/components/_reports/report-data-table/clientClass.js.map +0 -7
  136. package/dpr/components/_reports/report-data-table/types.d.js.map +0 -7
  137. package/dpr/components/_reports/report-data-table/utils.js +0 -123
  138. package/dpr/components/_reports/report-data-table/utils.js.map +0 -7
  139. package/dpr/components/_reports/report-data-table/utils.test.ts +0 -604
  140. package/dpr/components/_reports/report-data-table/utils.ts +0 -150
  141. package/dpr/components/_reports/report-data-table/view.njk +0 -24
  142. package/dpr/components/_reports/report-data-table-wrapper/view.njk +0 -27
  143. package/dpr/components/_reports/report-download-message/clientClass.js.map +0 -7
  144. package/dpr/components/_reports/report-no-data-message/styles.scss +0 -4
  145. package/dpr/components/_reports/report-no-data-message/view.njk +0 -13
  146. package/dpr/components/_reports/report-pagination/clientClass.js.map +0 -7
  147. package/dpr/components/_reports/report-print-message/view.njk +0 -8
  148. package/dpr/components/_reports/report-template/view.njk +0 -44
  149. package/dpr/components/_reports/report-wrapper/view.njk +0 -19
  150. package/dpr/components/loading-anim/styles.scss +0 -117
  151. package/dpr/components/loading-anim/view.njk +0 -18
  152. package/dpr/utils/CollatedSummaryBuilder/CollatedSummaryBuilder.js.map +0 -7
  153. package/dpr/utils/ParentChildDataTableBuilder/ParentChildDataTableBuilder.js +0 -202
  154. package/dpr/utils/ParentChildDataTableBuilder/ParentChildDataTableBuilder.js.map +0 -7
  155. package/dpr/utils/ParentChildDataTableBuilder/ParentChildDataTableBuilder.test.ts +0 -503
  156. package/dpr/utils/ParentChildDataTableBuilder/ParentChildDataTableBuilder.ts +0 -224
  157. package/dpr/utils/ParentChildDataTableBuilder/types.d.js.map +0 -7
  158. package/dpr/utils/ParentChildDataTableBuilder/types.d.ts +0 -11
  159. package/dpr/utils/SectionedDataTableBuilder/SectionedDataTableBuilder.js +0 -311
  160. package/dpr/utils/SectionedDataTableBuilder/SectionedDataTableBuilder.js.map +0 -7
  161. package/dpr/utils/SectionedDataTableBuilder/SectionedDataTableBuilder.test.ts +0 -492
  162. package/dpr/utils/SectionedDataTableBuilder/SectionedDataTableBuilder.ts +0 -342
  163. package/dpr/utils/SectionedDataTableBuilder/types.d.js.map +0 -7
  164. package/dpr/utils/SectionedDataTableBuilder/types.d.ts +0 -5
  165. package/dpr/utils/SectionedFieldsTableBuilder/SectionedFieldsTableBuilder.js +0 -146
  166. package/dpr/utils/SectionedFieldsTableBuilder/SectionedFieldsTableBuilder.js.map +0 -7
  167. package/dpr/utils/SectionedFieldsTableBuilder/SectionedFieldsTableBuilder.test.ts +0 -140
  168. package/dpr/utils/SectionedFieldsTableBuilder/SectionedFieldsTableBuilder.ts +0 -150
  169. /package/dpr/components/_reports/{report-actions → report-heading/report-actions}/actionsTemplate.js +0 -0
  170. /package/dpr/components/_reports/{report-actions → report-heading/report-actions}/actionsTemplate.ts +0 -0
  171. /package/dpr/components/_reports/{report-actions → report-heading/report-actions}/style.scss +0 -0
  172. /package/dpr/components/_reports/{report-actions → report-heading/report-actions}/types.d.js +0 -0
  173. /package/dpr/components/_reports/{report-actions → report-heading/report-actions}/utils.js +0 -0
  174. /package/dpr/components/_reports/{report-actions → report-heading/report-actions}/utils.ts +0 -0
  175. /package/dpr/components/_reports/{report-actions → report-heading/report-actions}/view.njk +0 -0
  176. /package/dpr/components/_reports/{report-columns-form → report-heading/report-columns/report-columns-form}/style.scss +0 -0
  177. /package/dpr/components/_reports/{report-columns-form → report-heading/report-columns/report-columns-form}/types.d.js +0 -0
  178. /package/dpr/components/_reports/{report-columns-form → report-heading/report-columns/report-columns-form}/types.d.ts +0 -0
  179. /package/dpr/components/_reports/{report-columns-form → report-heading/report-columns/report-columns-form}/view.njk +0 -0
  180. /package/dpr/components/_reports/{report-columns → report-heading/report-columns}/styles.scss +0 -0
  181. /package/dpr/components/_reports/{report-download-message → report-heading/report-download-message}/style.scss +0 -0
  182. /package/dpr/components/_reports/{report-download-message → report-heading/report-download-message}/view.njk +0 -0
  183. /package/dpr/components/_reports/{report-pagination → report-page/report-template/report-pagination}/style.scss +0 -0
  184. /package/dpr/components/_reports/{report-data-table → report-page/report-template/report-pagination}/types.d.js +0 -0
  185. /package/dpr/components/_reports/{report-pagination → report-page/report-template/report-pagination}/types.d.ts +0 -0
  186. /package/dpr/components/_reports/{report-pagination → report-page/report-template/report-pagination}/utils.js +0 -0
  187. /package/dpr/components/_reports/{report-pagination → report-page/report-template/report-pagination}/utils.test.ts +0 -0
  188. /package/dpr/components/_reports/{report-pagination → report-page/report-template/report-pagination}/utils.ts +0 -0
  189. /package/dpr/components/_reports/{report-pagination → report-page/report-template/report-pagination}/view.njk +0 -0
  190. /package/dpr/components/_reports/{report-pagination → report-page/report-template/report-section/report-data-table}/types.d.js +0 -0
  191. /package/dpr/components/_reports/{report-summary-table → report-page/report-template/report-summary-table}/view.njk +0 -0
  192. /package/dpr/components/_reports/{report-totals → report-page/report-template/report-totals}/style.scss +0 -0
  193. /package/dpr/components/_reports/{report-totals → report-page/report-template/report-totals}/utils.js +0 -0
  194. /package/dpr/components/_reports/{report-totals → report-page/report-template/report-totals}/utils.ts +0 -0
  195. /package/dpr/components/_reports/{report-totals → report-page/report-template/report-totals}/view.njk +0 -0
  196. /package/dpr/utils/{ParentChildDataTableBuilder → TemplateBuilder/ParentChildDataBuilder}/types.d.js +0 -0
  197. /package/dpr/utils/{SectionedDataTableBuilder → TemplateBuilder/ReportBuilder}/types.d.js +0 -0
@@ -1,7 +1,7 @@
1
1
  {
2
2
  "version": 3,
3
3
  "sources": ["../../dpr/types/ReportQuery.ts"],
4
- "sourcesContent": ["import type { ParsedQs } from 'qs'\nimport { FilteredListRequest } from './index'\nimport Dict = NodeJS.Dict\nimport { components } from './api'\nimport { clearFilterValue } from '../utils/urlHelper'\nimport ColumnUtils from '../components/_reports/report-columns-form/utils'\nimport { Template } from './Templates'\nimport { ReportType } from './UserReports'\n\nexport const DEFAULT_FILTERS_PREFIX = 'filters.'\n\nclass ReportQuery implements FilteredListRequest {\n selectedPage: number\n\n pageSize: number\n\n sortColumn?: string | undefined\n\n columns: Array<string>\n\n sortedAsc: boolean\n\n filters: Dict<string>\n\n filtersPrefix: string\n\n dataProductDefinitionsPath?: string | undefined\n\n constructor({\n fields,\n template,\n queryParams,\n definitionsPath,\n filtersPrefix = DEFAULT_FILTERS_PREFIX,\n reportType,\n }: {\n fields: components['schemas']['FieldDefinition'][]\n template?: Template\n queryParams: ParsedQs\n definitionsPath?: string\n filtersPrefix?: string\n reportType?: ReportType\n }) {\n this.selectedPage = queryParams['selectedPage'] ? Number(queryParams['selectedPage']) : 1\n this.pageSize = this.getPageSize(queryParams, template, reportType)\n\n this.sortColumn = queryParams['sortColumn']\n ? queryParams['sortColumn'].toString()\n : this.getDefaultSortColumn(fields)\n\n this.sortedAsc =\n queryParams['sortedAsc'] !== undefined\n ? queryParams['sortedAsc'] !== 'false'\n : this.getDefaultSortDirection(fields)\n\n this.dataProductDefinitionsPath =\n definitionsPath ??\n (queryParams['dataProductDefinitionsPath'] ? queryParams['dataProductDefinitionsPath'].toString() : undefined)\n\n this.filtersPrefix = filtersPrefix\n\n if (queryParams['columns']) {\n const columns =\n typeof queryParams['columns'] === 'string'\n ? queryParams['columns'].split(',')\n : (queryParams['columns'] as string[])\n this.columns = ColumnUtils.ensureMandatoryColumns(fields, columns)\n } else {\n this.columns = fields.filter((f) => f.visible).map((f) => f.name)\n }\n\n const dateField: components['schemas']['FieldDefinition'] | undefined = fields.find((f) => {\n return (\n (f.type === 'date' && f.filter && f.filter.type === 'daterange') ||\n (f.type === 'date' && f.filter && f.filter.type === 'date')\n )\n })\n\n let min: string | undefined\n let max: string | undefined\n if (dateField && dateField.filter) {\n min = dateField.filter.min\n max = dateField.filter.max\n }\n\n this.filters = {}\n\n Object.keys(queryParams)\n .filter((key) => key.startsWith(this.filtersPrefix))\n .filter((key) => queryParams[key])\n .forEach((key) => {\n const filter = key.replace(this.filtersPrefix, '')\n const p = queryParams[key]\n let value = p ? p.toString() : ''\n if (filter.includes('.start') && min) {\n if (new Date(value) < new Date(min)) value = min\n }\n if (filter.includes('.end') && max) {\n if (new Date(value) > new Date(max)) value = max\n }\n if (value !== 'no-filter') {\n this.filters[filter] = value\n }\n })\n\n if (dateField && dateField.filter && dateField.filter.type === 'daterange') {\n if (\n min &&\n Object.keys(queryParams).some((key) => key.includes(this.filtersPrefix)) &&\n Object.keys(queryParams).every((key) => !key.includes('.start'))\n ) {\n this.filters[`${dateField.name}.start`] = min\n }\n\n if (\n max &&\n Object.keys(queryParams).some((key) => key.includes(this.filtersPrefix)) &&\n Object.keys(queryParams).every((key) => !key.includes('.end'))\n ) {\n this.filters[`${dateField.name}.end`] = max\n }\n }\n\n if (dateField && dateField.filter && dateField.filter.type === 'date') {\n if (\n min &&\n Object.keys(queryParams).some((key) => key.includes(this.filtersPrefix)) &&\n Object.keys(queryParams).every((key) => !key.includes(dateField.name))\n ) {\n this.filters[`${dateField.name}.start`] = min\n }\n }\n }\n\n private getDefaultSortColumn(fields: components['schemas']['FieldDefinition'][]) {\n const defaultSortColumn = fields.find((f) => f.defaultsort)\n return defaultSortColumn ? defaultSortColumn.name : fields.find((f) => f.sortable)?.name\n }\n\n private getDefaultSortDirection(fields: components['schemas']['FieldDefinition'][]) {\n const field = fields.find((f) => f.defaultsort)\n if (field) {\n return field.sortDirection ? field.sortDirection === 'asc' : true\n }\n return true\n }\n\n getPageSize(queryParams: ParsedQs, template?: Template, reportType?: ReportType): number {\n let pageSize = 5000000\n if (!reportType || reportType === ReportType.REPORT) {\n if (queryParams['pageSize']) {\n pageSize = Number(queryParams['pageSize'])\n } else if (template) {\n pageSize = this.getDefaultPageSize(template)\n }\n }\n return pageSize\n }\n\n toRecordWithFilterPrefix(removeClearedFilters = false): Record<string, string | Array<string>> {\n const record: Record<string, string | Array<string>> = {\n selectedPage: this.selectedPage.toString(),\n ...(this.pageSize && { pageSize: this.pageSize.toString() }),\n ...(this.sortColumn && { sortColumn: this.sortColumn }),\n sortedAsc: this.sortedAsc.toString(),\n columns: this.columns,\n }\n\n if (this.dataProductDefinitionsPath) {\n record['dataProductDefinitionsPath'] = this.dataProductDefinitionsPath\n }\n\n Object.keys(this.filters).forEach((filterName) => {\n const value = this.filters[filterName]\n if ((value && !removeClearedFilters) || value !== clearFilterValue) {\n record[`${this.filtersPrefix}${filterName}`] = <string>value\n }\n })\n\n return record\n }\n\n private getDefaultPageSize(template: Template) {\n const maxResultsSize = 500000\n const standardPage = 20\n\n switch (template) {\n case 'list-section':\n case 'summary-section':\n case 'row-section-child':\n case 'parent-child':\n case 'parent-child-section':\n return maxResultsSize\n\n default:\n return standardPage\n }\n }\n}\n\nexport { ReportQuery }\nexport default ReportQuery\n"],
4
+ "sourcesContent": ["import type { ParsedQs } from 'qs'\nimport { FilteredListRequest } from './index'\nimport Dict = NodeJS.Dict\nimport { components } from './api'\nimport { clearFilterValue } from '../utils/urlHelper'\nimport ColumnUtils from '../components/_reports/report-heading/report-columns/report-columns-form/utils'\nimport { Template } from './Templates'\nimport { ReportType } from './UserReports'\n\nexport const DEFAULT_FILTERS_PREFIX = 'filters.'\n\nclass ReportQuery implements FilteredListRequest {\n selectedPage: number\n\n pageSize: number\n\n sortColumn?: string | undefined\n\n columns: Array<string>\n\n sortedAsc: boolean\n\n filters: Dict<string>\n\n filtersPrefix: string\n\n dataProductDefinitionsPath?: string | undefined\n\n constructor({\n fields,\n template,\n queryParams,\n definitionsPath,\n filtersPrefix = DEFAULT_FILTERS_PREFIX,\n reportType,\n }: {\n fields: components['schemas']['FieldDefinition'][]\n template?: Template\n queryParams: ParsedQs\n definitionsPath?: string\n filtersPrefix?: string\n reportType?: ReportType\n }) {\n this.selectedPage = queryParams['selectedPage'] ? Number(queryParams['selectedPage']) : 1\n this.pageSize = this.getPageSize(queryParams, template, reportType)\n\n this.sortColumn = queryParams['sortColumn']\n ? queryParams['sortColumn'].toString()\n : this.getDefaultSortColumn(fields)\n\n this.sortedAsc =\n queryParams['sortedAsc'] !== undefined\n ? queryParams['sortedAsc'] !== 'false'\n : this.getDefaultSortDirection(fields)\n\n this.dataProductDefinitionsPath =\n definitionsPath ??\n (queryParams['dataProductDefinitionsPath'] ? queryParams['dataProductDefinitionsPath'].toString() : undefined)\n\n this.filtersPrefix = filtersPrefix\n\n if (queryParams['columns']) {\n const columns =\n typeof queryParams['columns'] === 'string'\n ? queryParams['columns'].split(',')\n : (queryParams['columns'] as string[])\n this.columns = ColumnUtils.ensureMandatoryColumns(fields, columns)\n } else {\n this.columns = fields.filter((f) => f.visible).map((f) => f.name)\n }\n\n const dateField: components['schemas']['FieldDefinition'] | undefined = fields.find((f) => {\n return (\n (f.type === 'date' && f.filter && f.filter.type === 'daterange') ||\n (f.type === 'date' && f.filter && f.filter.type === 'date')\n )\n })\n\n let min: string | undefined\n let max: string | undefined\n if (dateField && dateField.filter) {\n min = dateField.filter.min\n max = dateField.filter.max\n }\n\n this.filters = {}\n\n Object.keys(queryParams)\n .filter((key) => key.startsWith(this.filtersPrefix))\n .filter((key) => queryParams[key])\n .forEach((key) => {\n const filter = key.replace(this.filtersPrefix, '')\n const p = queryParams[key]\n let value = p ? p.toString() : ''\n if (filter.includes('.start') && min) {\n if (new Date(value) < new Date(min)) value = min\n }\n if (filter.includes('.end') && max) {\n if (new Date(value) > new Date(max)) value = max\n }\n if (value !== 'no-filter') {\n this.filters[filter] = value\n }\n })\n\n if (dateField && dateField.filter && dateField.filter.type === 'daterange') {\n if (\n min &&\n Object.keys(queryParams).some((key) => key.includes(this.filtersPrefix)) &&\n Object.keys(queryParams).every((key) => !key.includes('.start'))\n ) {\n this.filters[`${dateField.name}.start`] = min\n }\n\n if (\n max &&\n Object.keys(queryParams).some((key) => key.includes(this.filtersPrefix)) &&\n Object.keys(queryParams).every((key) => !key.includes('.end'))\n ) {\n this.filters[`${dateField.name}.end`] = max\n }\n }\n\n if (dateField && dateField.filter && dateField.filter.type === 'date') {\n if (\n min &&\n Object.keys(queryParams).some((key) => key.includes(this.filtersPrefix)) &&\n Object.keys(queryParams).every((key) => !key.includes(dateField.name))\n ) {\n this.filters[`${dateField.name}.start`] = min\n }\n }\n }\n\n private getDefaultSortColumn(fields: components['schemas']['FieldDefinition'][]) {\n const defaultSortColumn = fields.find((f) => f.defaultsort)\n return defaultSortColumn ? defaultSortColumn.name : fields.find((f) => f.sortable)?.name\n }\n\n private getDefaultSortDirection(fields: components['schemas']['FieldDefinition'][]) {\n const field = fields.find((f) => f.defaultsort)\n if (field) {\n return field.sortDirection ? field.sortDirection === 'asc' : true\n }\n return true\n }\n\n getPageSize(queryParams: ParsedQs, template?: Template, reportType?: ReportType): number {\n let pageSize = 5000000\n if (!reportType || reportType === ReportType.REPORT) {\n if (queryParams['pageSize']) {\n pageSize = Number(queryParams['pageSize'])\n } else if (template) {\n pageSize = this.getDefaultPageSize(template)\n }\n }\n return pageSize\n }\n\n toRecordWithFilterPrefix(removeClearedFilters = false): Record<string, string | Array<string>> {\n const record: Record<string, string | Array<string>> = {\n selectedPage: this.selectedPage.toString(),\n ...(this.pageSize && { pageSize: this.pageSize.toString() }),\n ...(this.sortColumn && { sortColumn: this.sortColumn }),\n sortedAsc: this.sortedAsc.toString(),\n columns: this.columns,\n }\n\n if (this.dataProductDefinitionsPath) {\n record['dataProductDefinitionsPath'] = this.dataProductDefinitionsPath\n }\n\n Object.keys(this.filters).forEach((filterName) => {\n const value = this.filters[filterName]\n if ((value && !removeClearedFilters) || value !== clearFilterValue) {\n record[`${this.filtersPrefix}${filterName}`] = <string>value\n }\n })\n\n return record\n }\n\n private getDefaultPageSize(template: Template) {\n const maxResultsSize = 500000\n const standardPage = 20\n\n switch (template) {\n case 'list-section':\n case 'summary-section':\n case 'row-section-child':\n case 'parent-child':\n case 'parent-child-section':\n return maxResultsSize\n\n default:\n return standardPage\n }\n }\n}\n\nexport { ReportQuery }\nexport default ReportQuery\n"],
5
5
  "mappings": "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",
6
6
  "names": ["ColumnUtils"]
7
7
  }
@@ -3,7 +3,7 @@ import { FilteredListRequest } from './index'
3
3
  import Dict = NodeJS.Dict
4
4
  import { components } from './api'
5
5
  import { clearFilterValue } from '../utils/urlHelper'
6
- import ColumnUtils from '../components/_reports/report-columns-form/utils'
6
+ import ColumnUtils from '../components/_reports/report-heading/report-columns/report-columns-form/utils'
7
7
  import { Template } from './Templates'
8
8
  import { ReportType } from './UserReports'
9
9
 
@@ -1,7 +1,7 @@
1
1
  {
2
2
  "version": 3,
3
3
  "sources": ["../../dpr/types/UserReports.ts"],
4
- "sourcesContent": ["import Dict = NodeJS.Dict\nimport { SummaryTemplate, Template } from './Templates'\nimport { FieldDefinition } from '../utils/DataTableBuilder/types'\nimport { ChildReportExecutionData } from './ExecutionData'\n\nexport interface StoredReportData {\n reportId: string\n variantId?: string // NOTE variant ID exists fir V1 async routes\n id: string\n executionId?: string | undefined\n tableId?: string | undefined\n reportName: string\n variantName?: string\n name: string\n description: string\n status?: RequestStatus\n timestamp: AsyncReportsTimestamp\n dataProductDefinitionsPath?: string\n dpdPathFromQuery?: boolean\n query?: AsyncReportQueryData\n interactiveQuery?: AsyncReportQueryData\n url?: AsyncReportUrlData\n type: ReportType\n loadType?: LoadType\n childExecutionData?: Array<ChildReportExecutionData>\n}\n\nexport interface RequestedReport extends StoredReportData {\n template: Template\n errorMessage?: string\n filters: ParamsConfig\n sortBy: ParamsConfig\n}\n\nexport interface RequestedDashboard extends StoredReportData {\n metrics: { name: string }[]\n}\n\nexport type RecentlyViewedReport = StoredReportData\nexport type UserReportData = RequestedReport | RecentlyViewedReport | StoredReportData | RequestedDashboard\n\nexport interface AsyncReportUrlData {\n origin: string\n request?: AsyncReportUrlItemData\n report?: AsyncReportUrlItemData\n polling?: AsyncReportUrlItemData\n}\n\nexport interface AsyncReportUrlItemData {\n pathname?: string | undefined\n fullUrl?: string | undefined\n search?: string\n default?: string\n}\n\nexport interface AsyncReportQueryData {\n data: Dict<string | string[]>\n summary: Array<Dict<string>>\n}\n\nexport interface ParamsConfig {\n data: Dict<string>\n queryString: string\n}\n\nexport enum RequestStatus {\n SUBMITTED = 'SUBMITTED',\n STARTED = 'STARTED',\n PICKED = 'PICKED',\n FINISHED = 'FINISHED',\n FAILED = 'FAILED',\n ABORTED = 'ABORTED',\n EXPIRED = 'EXPIRED',\n READY = 'READY',\n ALL = 'ALL',\n}\n\nexport enum ReportType {\n REPORT = 'report',\n DASHBOARD = 'dashboard',\n UNAVAILABLE = 'unavailable',\n}\n\nexport interface AsyncReportsTimestamp {\n lastViewed?: Date\n requested?: Date\n completed?: Date\n expired?: Date\n failed?: Date\n retried?: Date\n aborted?: Date\n refresh?: Date\n}\n\nexport interface AsyncSummary {\n id: string\n template: SummaryTemplate\n fields: Array<FieldDefinition>\n data: Array<Dict<string>>\n}\n\nexport interface FormattedUserReportData {\n id?: string | undefined\n href?: string | undefined\n text: string\n reportName: string\n description: string\n timestamp?: string\n tag?: string\n status?: string | undefined\n type: ReportType\n summary?: { name: string; value: string }[]\n interactiveSummary?: { name: string; value: string }[]\n meta: meta\n}\n\nexport interface FormattedBookmarkData {\n id?: string\n href?: string\n text: string\n reportName: string\n description: string\n timestamp?: string\n tag?: string\n status?: string\n type: ReportType\n summary?: { name: string; value: string }[]\n interactiveSummary?: { name: string; value: string }[]\n}\n\nexport interface meta {\n reportId: string\n id: string\n executionId?: string | undefined\n tableId?: string | undefined\n status?: string | undefined\n type: ReportType\n requestedAt?: Date | undefined\n dataProductDefinitionsPath?: string | undefined\n pollingUrl?: string | undefined\n reportUrl?: string | undefined\n}\n\nexport interface RequestFormData {\n dataProductDefinitionsPath: string\n _csrf: string\n reportId: string\n name: string\n reportName: string\n description: string\n type: string\n pathname: string\n origin: string\n href: string\n search: string\n id: string\n variantId?: string\n template?: string\n metrics?: { name: string }[]\n}\n\nexport enum LoadType {\n SYNC = 'sync',\n ASYNC = 'async',\n SCHEDULED = 'scheduled',\n}\n\nexport interface DefinitionData {\n reportName: string\n reportId: string\n id: string\n name: string\n description?: string\n type: ReportType\n reportDescription?: string\n loadType: LoadType\n authorised: boolean\n isMissing?: boolean\n}\n"],
4
+ "sourcesContent": ["import Dict = NodeJS.Dict\nimport { SummaryTemplate, Template } from './Templates'\nimport { ChildReportExecutionData } from './ExecutionData'\nimport { components } from './api'\n\nexport interface StoredReportData {\n reportId: string\n variantId?: string // NOTE variant ID exists fir V1 async routes\n id: string\n executionId?: string | undefined\n tableId?: string | undefined\n reportName: string\n variantName?: string\n name: string\n description: string\n status?: RequestStatus\n timestamp: AsyncReportsTimestamp\n dataProductDefinitionsPath?: string\n dpdPathFromQuery?: boolean\n query?: AsyncReportQueryData\n interactiveQuery?: AsyncReportQueryData\n url?: AsyncReportUrlData\n type: ReportType\n loadType?: LoadType\n childExecutionData?: Array<ChildReportExecutionData>\n}\n\nexport interface RequestedReport extends StoredReportData {\n template: Template\n errorMessage?: string\n filters: ParamsConfig\n sortBy: ParamsConfig\n}\n\nexport interface RequestedDashboard extends StoredReportData {\n metrics: { name: string }[]\n}\n\nexport type RecentlyViewedReport = StoredReportData\nexport type UserReportData = RequestedReport | RecentlyViewedReport | StoredReportData | RequestedDashboard\n\nexport interface AsyncReportUrlData {\n origin: string\n request?: AsyncReportUrlItemData\n report?: AsyncReportUrlItemData\n polling?: AsyncReportUrlItemData\n}\n\nexport interface AsyncReportUrlItemData {\n pathname?: string | undefined\n fullUrl?: string | undefined\n search?: string\n default?: string\n}\n\nexport interface AsyncReportQueryData {\n data: Dict<string | string[]>\n summary: Array<Dict<string>>\n}\n\nexport interface ParamsConfig {\n data: Dict<string>\n queryString: string\n}\n\nexport enum RequestStatus {\n SUBMITTED = 'SUBMITTED',\n STARTED = 'STARTED',\n PICKED = 'PICKED',\n FINISHED = 'FINISHED',\n FAILED = 'FAILED',\n ABORTED = 'ABORTED',\n EXPIRED = 'EXPIRED',\n READY = 'READY',\n ALL = 'ALL',\n}\n\nexport enum ReportType {\n REPORT = 'report',\n DASHBOARD = 'dashboard',\n UNAVAILABLE = 'unavailable',\n}\n\nexport interface AsyncReportsTimestamp {\n lastViewed?: Date\n requested?: Date\n completed?: Date\n expired?: Date\n failed?: Date\n retried?: Date\n aborted?: Date\n refresh?: Date\n}\n\nexport interface AsyncSummary {\n id: string\n template: SummaryTemplate\n fields: Array<components['schemas']['SummaryField']>\n data: Array<Record<string, string>>\n}\n\nexport interface FormattedUserReportData {\n id?: string | undefined\n href?: string | undefined\n text: string\n reportName: string\n description: string\n timestamp?: string\n tag?: string\n status?: string | undefined\n type: ReportType\n summary?: { name: string; value: string }[]\n interactiveSummary?: { name: string; value: string }[]\n meta: meta\n}\n\nexport interface FormattedBookmarkData {\n id?: string\n href?: string\n text: string\n reportName: string\n description: string\n timestamp?: string\n tag?: string\n status?: string\n type: ReportType\n summary?: { name: string; value: string }[]\n interactiveSummary?: { name: string; value: string }[]\n}\n\nexport interface meta {\n reportId: string\n id: string\n executionId?: string | undefined\n tableId?: string | undefined\n status?: string | undefined\n type: ReportType\n requestedAt?: Date | undefined\n dataProductDefinitionsPath?: string | undefined\n pollingUrl?: string | undefined\n reportUrl?: string | undefined\n}\n\nexport interface RequestFormData {\n dataProductDefinitionsPath: string\n _csrf: string\n reportId: string\n name: string\n reportName: string\n description: string\n type: string\n pathname: string\n origin: string\n href: string\n search: string\n id: string\n variantId?: string\n template?: string\n metrics?: { name: string }[]\n}\n\nexport enum LoadType {\n SYNC = 'sync',\n ASYNC = 'async',\n SCHEDULED = 'scheduled',\n}\n\nexport interface DefinitionData {\n reportName: string\n reportId: string\n id: string\n name: string\n description?: string\n type: ReportType\n reportDescription?: string\n loadType: LoadType\n authorised: boolean\n isMissing?: boolean\n}\n"],
5
5
  "mappings": ";;;;;;;;;;;;;;;;;;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAAA;AAiEO,IAAK,gBAAL,kBAAKA,mBAAL;AACL,EAAAA,eAAA,eAAY;AACZ,EAAAA,eAAA,aAAU;AACV,EAAAA,eAAA,YAAS;AACT,EAAAA,eAAA,cAAW;AACX,EAAAA,eAAA,YAAS;AACT,EAAAA,eAAA,aAAU;AACV,EAAAA,eAAA,aAAU;AACV,EAAAA,eAAA,WAAQ;AACR,EAAAA,eAAA,SAAM;AATI,SAAAA;AAAA,GAAA;AAYL,IAAK,aAAL,kBAAKC,gBAAL;AACL,EAAAA,YAAA,YAAS;AACT,EAAAA,YAAA,eAAY;AACZ,EAAAA,YAAA,iBAAc;AAHJ,SAAAA;AAAA,GAAA;AAoFL,IAAK,WAAL,kBAAKC,cAAL;AACL,EAAAA,UAAA,UAAO;AACP,EAAAA,UAAA,WAAQ;AACR,EAAAA,UAAA,eAAY;AAHF,SAAAA;AAAA,GAAA;",
6
6
  "names": ["RequestStatus", "ReportType", "LoadType"]
7
7
  }
@@ -1,7 +1,7 @@
1
1
  import Dict = NodeJS.Dict
2
2
  import { SummaryTemplate, Template } from './Templates'
3
- import { FieldDefinition } from '../utils/DataTableBuilder/types'
4
3
  import { ChildReportExecutionData } from './ExecutionData'
4
+ import { components } from './api'
5
5
 
6
6
  export interface StoredReportData {
7
7
  reportId: string
@@ -95,8 +95,8 @@ export interface AsyncReportsTimestamp {
95
95
  export interface AsyncSummary {
96
96
  id: string
97
97
  template: SummaryTemplate
98
- fields: Array<FieldDefinition>
99
- data: Array<Dict<string>>
98
+ fields: Array<components['schemas']['SummaryField']>
99
+ data: Array<Record<string, string>>
100
100
  }
101
101
 
102
102
  export interface FormattedUserReportData {
@@ -0,0 +1,193 @@
1
+ "use strict";
2
+ var __create = Object.create;
3
+ var __defProp = Object.defineProperty;
4
+ var __getOwnPropDesc = Object.getOwnPropertyDescriptor;
5
+ var __getOwnPropNames = Object.getOwnPropertyNames;
6
+ var __getProtoOf = Object.getPrototypeOf;
7
+ var __hasOwnProp = Object.prototype.hasOwnProperty;
8
+ var __export = (target, all) => {
9
+ for (var name in all)
10
+ __defProp(target, name, { get: all[name], enumerable: true });
11
+ };
12
+ var __copyProps = (to, from, except, desc) => {
13
+ if (from && typeof from === "object" || typeof from === "function") {
14
+ for (let key of __getOwnPropNames(from))
15
+ if (!__hasOwnProp.call(to, key) && key !== except)
16
+ __defProp(to, key, { get: () => from[key], enumerable: !(desc = __getOwnPropDesc(from, key)) || desc.enumerable });
17
+ }
18
+ return to;
19
+ };
20
+ var __toESM = (mod, isNodeMode, target) => (target = mod != null ? __create(__getProtoOf(mod)) : {}, __copyProps(
21
+ // If the importer is in node compatibility mode or this is not an ESM
22
+ // file that has been converted to a CommonJS file using a Babel-
23
+ // compatible transform (i.e. "__esModule" has not been set), then set
24
+ // "default" to the CommonJS "module.exports" for node compatibility.
25
+ isNodeMode || !mod || !mod.__esModule ? __defProp(target, "default", { value: mod, enumerable: true }) : target,
26
+ mod
27
+ ));
28
+ var __toCommonJS = (mod) => __copyProps(__defProp({}, "__esModule", { value: true }), mod);
29
+ var ParentChildDataBuilder_exports = {};
30
+ __export(ParentChildDataBuilder_exports, {
31
+ ParentChildDataBuilder: () => ParentChildDataBuilder
32
+ });
33
+ module.exports = __toCommonJS(ParentChildDataBuilder_exports);
34
+ var import_DataTableBuilder = __toESM(require("../../DataTableBuilder/DataTableBuilder"));
35
+ var import_SectionedDataHelper = require("../SectionedDataHelper/SectionedDataHelper");
36
+ var import_TemplateBuilder = require("../TemplateBuilder");
37
+ class ParentChildDataBuilder extends import_TemplateBuilder.TemplateBuilder {
38
+ childColumns = [];
39
+ childVariants = [];
40
+ childData = [];
41
+ joinFields = [];
42
+ childFields = [];
43
+ parentChildDatasets = [];
44
+ dataTableBuilder;
45
+ constructor(variant) {
46
+ super(variant);
47
+ this.childVariants = this.variant.childVariants || [];
48
+ }
49
+ getChildVariant(childId) {
50
+ return this.childVariants.find((cv) => cv.id === childId);
51
+ }
52
+ /**
53
+ * Exracts the relevant data from the child variant definition
54
+ * to generate the child table
55
+ *
56
+ * @param {string} childId
57
+ * @return { fields: components['schemas']['FieldDefinition'][], joinFields: string[], columns: string[], name: string }
58
+ * @memberof ParentChildDataBuilder
59
+ */
60
+ getChildVariantDefinitionData(childId) {
61
+ const childVariant = this.getChildVariant(childId);
62
+ let fields = [];
63
+ let joinFields = [];
64
+ let columns = [];
65
+ let name = "Child report";
66
+ if (childVariant && childVariant.specification) {
67
+ fields = childVariant.specification.fields;
68
+ joinFields = childVariant && childVariant.specification ? childVariant.joinFields : [];
69
+ columns = fields.filter((f) => f.visible).map((f) => f.name);
70
+ name = childVariant.name;
71
+ }
72
+ return {
73
+ fields,
74
+ joinFields,
75
+ columns,
76
+ name
77
+ };
78
+ }
79
+ /**
80
+ * Maps the parent child rows.
81
+ * Splits into sections that will become the parent table
82
+ *
83
+ * @return {*} {GroupedParentChildDataset[]}
84
+ * @memberof ParentChildDataBuilder
85
+ */
86
+ mergeParentChildAndGroup(parentData) {
87
+ const groups = [];
88
+ let pendingParents = [];
89
+ parentData.forEach((parentRow) => {
90
+ const dataset = {
91
+ parent: parentRow,
92
+ children: []
93
+ };
94
+ this.childData.forEach((child) => {
95
+ const { joinFields } = this.getChildVariantDefinitionData(child.id);
96
+ const matchedChildren = [];
97
+ child.data.forEach((childRow) => {
98
+ const isMatch = joinFields.every((col) => {
99
+ return parentRow[col] === childRow[col];
100
+ });
101
+ if (isMatch) matchedChildren.push(childRow);
102
+ });
103
+ if (matchedChildren.length) {
104
+ dataset.children.push({
105
+ id: child.id,
106
+ data: matchedChildren
107
+ });
108
+ }
109
+ });
110
+ pendingParents.push(dataset.parent);
111
+ if (dataset.children.length > 0) {
112
+ groups.push({
113
+ parent: pendingParents,
114
+ children: dataset.children
115
+ });
116
+ pendingParents = [];
117
+ }
118
+ });
119
+ if (pendingParents.length > 0) {
120
+ groups.push({
121
+ parent: pendingParents,
122
+ children: []
123
+ });
124
+ }
125
+ return groups;
126
+ }
127
+ /**
128
+ * Maps the parent child data to a table data
129
+ *
130
+ * @param {GroupedParentChildDataset[]} parentChildGroups
131
+ * @return {*} {ParentChildData[]}
132
+ * @memberof ParentChildDataBuilder
133
+ */
134
+ mapToTableData(parentChildGroups) {
135
+ const parentTableBuilder = new import_DataTableBuilder.default(this.fields);
136
+ return parentChildGroups.map((group) => {
137
+ const parentTable = parentTableBuilder.withNoHeaderOptions(this.columns).buildTable(group.parent);
138
+ const children = this.mapChildDataToTableData(group);
139
+ return {
140
+ parent: parentTable,
141
+ children
142
+ };
143
+ });
144
+ }
145
+ /**
146
+ * Maps the grouped child data to table data
147
+ *
148
+ * @param {GroupedParentChildDataset} group
149
+ * @return {*}
150
+ * @memberof ParentChildDataBuilder
151
+ */
152
+ mapChildDataToTableData(group) {
153
+ return group.children.map((child) => {
154
+ const { fields: childFields, columns: childColumns, name } = this.getChildVariantDefinitionData(child.id);
155
+ const childTableBuilder = new import_DataTableBuilder.default(childFields);
156
+ const childTable = childTableBuilder.withNoHeaderOptions(childColumns).buildTable(child.data);
157
+ return {
158
+ title: name,
159
+ ...childTable
160
+ };
161
+ });
162
+ }
163
+ withChildData(childData) {
164
+ this.childData = childData;
165
+ return this;
166
+ }
167
+ withChildColumns(childColumns) {
168
+ this.childColumns = childColumns;
169
+ return this;
170
+ }
171
+ build() {
172
+ const sectionData = new import_SectionedDataHelper.SectionedDataHelper().withSections(this.sections).withData(this.data).withFields(this.fields).withReportQuery(this.reportQuery).build();
173
+ const { sections } = sectionData;
174
+ const mappedSections = sections.map((section) => {
175
+ const groups = this.mergeParentChildAndGroup(section.data);
176
+ const table = this.mapToTableData(groups);
177
+ return {
178
+ ...section,
179
+ summaries: [],
180
+ data: table
181
+ };
182
+ });
183
+ return {
184
+ rowCount: this.data.length,
185
+ sections: mappedSections
186
+ };
187
+ }
188
+ }
189
+ // Annotate the CommonJS export names for ESM import in node:
190
+ 0 && (module.exports = {
191
+ ParentChildDataBuilder
192
+ });
193
+ //# sourceMappingURL=ParentChildDataBuilder.js.map
@@ -0,0 +1,7 @@
1
+ {
2
+ "version": 3,
3
+ "sources": ["../../../../dpr/utils/TemplateBuilder/ParentChildDataBuilder/ParentChildDataBuilder.ts"],
4
+ "sourcesContent": ["import { components } from '../../../types/api'\nimport DataTableBuilder from '../../DataTableBuilder/DataTableBuilder'\nimport { DataTable } from '../../DataTableBuilder/types'\nimport { SectionedDataHelper } from '../SectionedDataHelper/SectionedDataHelper'\nimport { ReportTemplateData, SectionData } from '../SectionedDataHelper/types'\nimport { TemplateBuilder } from '../TemplateBuilder'\nimport { ChildData, GroupedParentChildDataset, ParentChildTableData, ParentChildDataset } from './types'\n\nexport class ParentChildDataBuilder extends TemplateBuilder {\n childColumns: Array<string> = []\n\n childVariants: components['schemas']['ChildVariantDefinition'][] = []\n\n childData: Array<ChildData> = []\n\n joinFields: Array<components['schemas']['FieldDefinition']> = []\n\n childFields: Array<components['schemas']['FieldDefinition']> = []\n\n parentChildDatasets: ParentChildDataset[] = []\n\n dataTableBuilder!: DataTableBuilder\n\n constructor(variant: components['schemas']['VariantDefinition']) {\n super(variant)\n\n this.childVariants = this.variant.childVariants || []\n }\n\n getChildVariant(childId: string) {\n return this.childVariants.find((cv) => cv.id === childId)\n }\n\n /**\n * Exracts the relevant data from the child variant definition\n * to generate the child table\n *\n * @param {string} childId\n * @return { fields: components['schemas']['FieldDefinition'][], joinFields: string[], columns: string[], name: string }\n * @memberof ParentChildDataBuilder\n */\n getChildVariantDefinitionData(childId: string) {\n const childVariant = this.getChildVariant(childId)\n\n let fields: components['schemas']['FieldDefinition'][] = []\n let joinFields: string[] = []\n let columns: string[] = []\n let name = 'Child report'\n\n if (childVariant && childVariant.specification) {\n fields = childVariant.specification.fields\n joinFields = childVariant && childVariant.specification ? childVariant.joinFields : []\n columns = fields.filter((f) => f.visible).map((f) => f.name)\n name = childVariant.name\n }\n\n return {\n fields,\n joinFields,\n columns,\n name,\n }\n }\n\n /**\n * Maps the parent child rows.\n * Splits into sections that will become the parent table\n *\n * @return {*} {GroupedParentChildDataset[]}\n * @memberof ParentChildDataBuilder\n */\n mergeParentChildAndGroup(parentData: Record<string, string>[]): GroupedParentChildDataset[] {\n const groups: GroupedParentChildDataset[] = []\n let pendingParents: Array<Record<string, string>> = []\n\n parentData.forEach((parentRow) => {\n // Build a dataset for this parent\n const dataset: ParentChildDataset = {\n parent: parentRow,\n children: [],\n }\n\n // Match against each child dataset\n this.childData.forEach((child) => {\n const { joinFields } = this.getChildVariantDefinitionData(child.id)\n const matchedChildren: Record<string, string>[] = []\n\n // Compare join fields\n child.data.forEach((childRow) => {\n const isMatch = joinFields.every((col) => {\n return parentRow[col] === childRow[col]\n })\n if (isMatch) matchedChildren.push(childRow)\n })\n\n if (matchedChildren.length) {\n dataset.children.push({\n id: child.id,\n data: matchedChildren,\n })\n }\n })\n\n // Always collect the parent\n pendingParents.push(dataset.parent)\n\n // If dataset has children \u2192 close the group\n if (dataset.children.length > 0) {\n groups.push({\n parent: pendingParents,\n children: dataset.children,\n })\n pendingParents = []\n }\n })\n\n // If leftover parents exist, make a final group (empty children)\n if (pendingParents.length > 0) {\n groups.push({\n parent: pendingParents,\n children: [],\n })\n }\n\n return groups\n }\n\n /**\n * Maps the parent child data to a table data\n *\n * @param {GroupedParentChildDataset[]} parentChildGroups\n * @return {*} {ParentChildData[]}\n * @memberof ParentChildDataBuilder\n */\n mapToTableData(parentChildGroups: GroupedParentChildDataset[]): ParentChildTableData[] {\n const parentTableBuilder = new DataTableBuilder(this.fields)\n return parentChildGroups.map((group: GroupedParentChildDataset) => {\n const parentTable = parentTableBuilder.withNoHeaderOptions(this.columns).buildTable(group.parent)\n const children: ParentChildTableData['children'] = this.mapChildDataToTableData(group)\n\n return {\n parent: parentTable,\n children,\n }\n })\n }\n\n /**\n * Maps the grouped child data to table data\n *\n * @param {GroupedParentChildDataset} group\n * @return {*}\n * @memberof ParentChildDataBuilder\n */\n mapChildDataToTableData(group: GroupedParentChildDataset) {\n return group.children.map((child) => {\n const { fields: childFields, columns: childColumns, name } = this.getChildVariantDefinitionData(child.id)\n const childTableBuilder = new DataTableBuilder(childFields)\n const childTable = childTableBuilder.withNoHeaderOptions(childColumns).buildTable(child.data)\n\n return {\n title: name,\n ...childTable,\n }\n })\n }\n\n withChildData(childData: Array<ChildData>) {\n this.childData = childData\n return this\n }\n\n withChildColumns(childColumns: string[]) {\n this.childColumns = childColumns\n return this\n }\n\n build(): ReportTemplateData {\n const sectionData = new SectionedDataHelper()\n .withSections(this.sections)\n .withData(this.data)\n .withFields(this.fields)\n .withReportQuery(this.reportQuery)\n .build()\n\n const { sections } = sectionData\n const mappedSections = sections.map((section: SectionData) => {\n const groups = this.mergeParentChildAndGroup(<Array<Record<string, string>>>section.data)\n const table = this.mapToTableData(groups)\n\n return {\n ...section,\n summaries: [] as unknown as Record<string, DataTable[]>,\n data: table,\n }\n })\n\n return {\n rowCount: this.data.length,\n sections: mappedSections,\n }\n }\n}\n"],
5
+ "mappings": "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",
6
+ "names": ["DataTableBuilder"]
7
+ }
@@ -0,0 +1,203 @@
1
+ import { components } from '../../../types/api'
2
+ import DataTableBuilder from '../../DataTableBuilder/DataTableBuilder'
3
+ import { DataTable } from '../../DataTableBuilder/types'
4
+ import { SectionedDataHelper } from '../SectionedDataHelper/SectionedDataHelper'
5
+ import { ReportTemplateData, SectionData } from '../SectionedDataHelper/types'
6
+ import { TemplateBuilder } from '../TemplateBuilder'
7
+ import { ChildData, GroupedParentChildDataset, ParentChildTableData, ParentChildDataset } from './types'
8
+
9
+ export class ParentChildDataBuilder extends TemplateBuilder {
10
+ childColumns: Array<string> = []
11
+
12
+ childVariants: components['schemas']['ChildVariantDefinition'][] = []
13
+
14
+ childData: Array<ChildData> = []
15
+
16
+ joinFields: Array<components['schemas']['FieldDefinition']> = []
17
+
18
+ childFields: Array<components['schemas']['FieldDefinition']> = []
19
+
20
+ parentChildDatasets: ParentChildDataset[] = []
21
+
22
+ dataTableBuilder!: DataTableBuilder
23
+
24
+ constructor(variant: components['schemas']['VariantDefinition']) {
25
+ super(variant)
26
+
27
+ this.childVariants = this.variant.childVariants || []
28
+ }
29
+
30
+ getChildVariant(childId: string) {
31
+ return this.childVariants.find((cv) => cv.id === childId)
32
+ }
33
+
34
+ /**
35
+ * Exracts the relevant data from the child variant definition
36
+ * to generate the child table
37
+ *
38
+ * @param {string} childId
39
+ * @return { fields: components['schemas']['FieldDefinition'][], joinFields: string[], columns: string[], name: string }
40
+ * @memberof ParentChildDataBuilder
41
+ */
42
+ getChildVariantDefinitionData(childId: string) {
43
+ const childVariant = this.getChildVariant(childId)
44
+
45
+ let fields: components['schemas']['FieldDefinition'][] = []
46
+ let joinFields: string[] = []
47
+ let columns: string[] = []
48
+ let name = 'Child report'
49
+
50
+ if (childVariant && childVariant.specification) {
51
+ fields = childVariant.specification.fields
52
+ joinFields = childVariant && childVariant.specification ? childVariant.joinFields : []
53
+ columns = fields.filter((f) => f.visible).map((f) => f.name)
54
+ name = childVariant.name
55
+ }
56
+
57
+ return {
58
+ fields,
59
+ joinFields,
60
+ columns,
61
+ name,
62
+ }
63
+ }
64
+
65
+ /**
66
+ * Maps the parent child rows.
67
+ * Splits into sections that will become the parent table
68
+ *
69
+ * @return {*} {GroupedParentChildDataset[]}
70
+ * @memberof ParentChildDataBuilder
71
+ */
72
+ mergeParentChildAndGroup(parentData: Record<string, string>[]): GroupedParentChildDataset[] {
73
+ const groups: GroupedParentChildDataset[] = []
74
+ let pendingParents: Array<Record<string, string>> = []
75
+
76
+ parentData.forEach((parentRow) => {
77
+ // Build a dataset for this parent
78
+ const dataset: ParentChildDataset = {
79
+ parent: parentRow,
80
+ children: [],
81
+ }
82
+
83
+ // Match against each child dataset
84
+ this.childData.forEach((child) => {
85
+ const { joinFields } = this.getChildVariantDefinitionData(child.id)
86
+ const matchedChildren: Record<string, string>[] = []
87
+
88
+ // Compare join fields
89
+ child.data.forEach((childRow) => {
90
+ const isMatch = joinFields.every((col) => {
91
+ return parentRow[col] === childRow[col]
92
+ })
93
+ if (isMatch) matchedChildren.push(childRow)
94
+ })
95
+
96
+ if (matchedChildren.length) {
97
+ dataset.children.push({
98
+ id: child.id,
99
+ data: matchedChildren,
100
+ })
101
+ }
102
+ })
103
+
104
+ // Always collect the parent
105
+ pendingParents.push(dataset.parent)
106
+
107
+ // If dataset has children → close the group
108
+ if (dataset.children.length > 0) {
109
+ groups.push({
110
+ parent: pendingParents,
111
+ children: dataset.children,
112
+ })
113
+ pendingParents = []
114
+ }
115
+ })
116
+
117
+ // If leftover parents exist, make a final group (empty children)
118
+ if (pendingParents.length > 0) {
119
+ groups.push({
120
+ parent: pendingParents,
121
+ children: [],
122
+ })
123
+ }
124
+
125
+ return groups
126
+ }
127
+
128
+ /**
129
+ * Maps the parent child data to a table data
130
+ *
131
+ * @param {GroupedParentChildDataset[]} parentChildGroups
132
+ * @return {*} {ParentChildData[]}
133
+ * @memberof ParentChildDataBuilder
134
+ */
135
+ mapToTableData(parentChildGroups: GroupedParentChildDataset[]): ParentChildTableData[] {
136
+ const parentTableBuilder = new DataTableBuilder(this.fields)
137
+ return parentChildGroups.map((group: GroupedParentChildDataset) => {
138
+ const parentTable = parentTableBuilder.withNoHeaderOptions(this.columns).buildTable(group.parent)
139
+ const children: ParentChildTableData['children'] = this.mapChildDataToTableData(group)
140
+
141
+ return {
142
+ parent: parentTable,
143
+ children,
144
+ }
145
+ })
146
+ }
147
+
148
+ /**
149
+ * Maps the grouped child data to table data
150
+ *
151
+ * @param {GroupedParentChildDataset} group
152
+ * @return {*}
153
+ * @memberof ParentChildDataBuilder
154
+ */
155
+ mapChildDataToTableData(group: GroupedParentChildDataset) {
156
+ return group.children.map((child) => {
157
+ const { fields: childFields, columns: childColumns, name } = this.getChildVariantDefinitionData(child.id)
158
+ const childTableBuilder = new DataTableBuilder(childFields)
159
+ const childTable = childTableBuilder.withNoHeaderOptions(childColumns).buildTable(child.data)
160
+
161
+ return {
162
+ title: name,
163
+ ...childTable,
164
+ }
165
+ })
166
+ }
167
+
168
+ withChildData(childData: Array<ChildData>) {
169
+ this.childData = childData
170
+ return this
171
+ }
172
+
173
+ withChildColumns(childColumns: string[]) {
174
+ this.childColumns = childColumns
175
+ return this
176
+ }
177
+
178
+ build(): ReportTemplateData {
179
+ const sectionData = new SectionedDataHelper()
180
+ .withSections(this.sections)
181
+ .withData(this.data)
182
+ .withFields(this.fields)
183
+ .withReportQuery(this.reportQuery)
184
+ .build()
185
+
186
+ const { sections } = sectionData
187
+ const mappedSections = sections.map((section: SectionData) => {
188
+ const groups = this.mergeParentChildAndGroup(<Array<Record<string, string>>>section.data)
189
+ const table = this.mapToTableData(groups)
190
+
191
+ return {
192
+ ...section,
193
+ summaries: [] as unknown as Record<string, DataTable[]>,
194
+ data: table,
195
+ }
196
+ })
197
+
198
+ return {
199
+ rowCount: this.data.length,
200
+ sections: mappedSections,
201
+ }
202
+ }
203
+ }
@@ -0,0 +1,7 @@
1
+ {
2
+ "version": 3,
3
+ "sources": ["../../../../dpr/utils/TemplateBuilder/ParentChildDataBuilder/types.d.ts"],
4
+ "sourcesContent": ["import { Cell } from '../../DataTableBuilder/types'\n\nexport interface ChildData {\n id: string\n data: Array<Record<string, string>>\n}\n\nexport interface ParentChildTableData {\n parent: {\n head: Cell[] | null\n rows: Cell[][]\n }\n children: {\n title: string\n head: Cell[] | null\n rows: Cell[][]\n }[]\n}\n\nexport interface ParentChildDataset {\n parent: Record<string, string>\n children: ChildData[]\n}\n\nexport interface GroupedParentChildDataset {\n parent: Array<Record<string, string>>\n children: ChildData[]\n}\nexport interface ParentChildTemplateData {\n rowCount: number\n sections: {\n title?: string\n count?: number\n data: ParentChildTableData[]\n }[]\n}\n"],
5
+ "mappings": ";;;;;;;;;;;;;;AAAA;AAAA;",
6
+ "names": []
7
+ }
@@ -0,0 +1,36 @@
1
+ import { Cell } from '../../DataTableBuilder/types'
2
+
3
+ export interface ChildData {
4
+ id: string
5
+ data: Array<Record<string, string>>
6
+ }
7
+
8
+ export interface ParentChildTableData {
9
+ parent: {
10
+ head: Cell[] | null
11
+ rows: Cell[][]
12
+ }
13
+ children: {
14
+ title: string
15
+ head: Cell[] | null
16
+ rows: Cell[][]
17
+ }[]
18
+ }
19
+
20
+ export interface ParentChildDataset {
21
+ parent: Record<string, string>
22
+ children: ChildData[]
23
+ }
24
+
25
+ export interface GroupedParentChildDataset {
26
+ parent: Array<Record<string, string>>
27
+ children: ChildData[]
28
+ }
29
+ export interface ParentChildTemplateData {
30
+ rowCount: number
31
+ sections: {
32
+ title?: string
33
+ count?: number
34
+ data: ParentChildTableData[]
35
+ }[]
36
+ }