@gen3/frontend 0.11.11 → 0.11.13

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 (251) hide show
  1. package/dist/cjs/index.js +1216 -855
  2. package/dist/cjs/index.js.map +1 -1
  3. package/dist/dts/components/DropdownWithIcon/DropdownWithIcon.d.ts +16 -10
  4. package/dist/dts/components/DropdownWithIcon/DropdownWithIcon.d.ts.map +1 -1
  5. package/dist/dts/components/DropdownWithIcon/DropdownWithIcon.js +24 -13
  6. package/dist/dts/components/DropdownWithIcon/DropdownWithIcon.js.map +1 -1
  7. package/dist/dts/components/DropdownWithIcon/DropdownWithIcon.unit.test.js +43 -30
  8. package/dist/dts/components/DropdownWithIcon/DropdownWithIcon.unit.test.js.map +1 -1
  9. package/dist/dts/components/MessageCards/ErrorMessage.js +1 -1
  10. package/dist/dts/components/MessageCards/ErrorMessage.js.map +1 -1
  11. package/dist/dts/components/Providers/Gen3Provider.d.ts +141 -4
  12. package/dist/dts/components/Providers/Gen3Provider.d.ts.map +1 -1
  13. package/dist/dts/components/charts/Charts.d.ts.map +1 -1
  14. package/dist/dts/components/charts/Charts.js +27 -31
  15. package/dist/dts/components/charts/Charts.js.map +1 -1
  16. package/dist/dts/components/charts/CollapsableCharts.d.ts +2 -2
  17. package/dist/dts/components/charts/CollapsableCharts.d.ts.map +1 -1
  18. package/dist/dts/components/charts/CollapsableCharts.js +2 -2
  19. package/dist/dts/components/charts/CollapsableCharts.js.map +1 -1
  20. package/dist/dts/components/charts/createChart.d.ts.map +1 -1
  21. package/dist/dts/components/charts/createChart.js +7 -12
  22. package/dist/dts/components/charts/createChart.js.map +1 -1
  23. package/dist/dts/components/charts/echarts/HorizontalBarChart.d.ts.map +1 -1
  24. package/dist/dts/components/charts/echarts/HorizontalBarChart.js +7 -4
  25. package/dist/dts/components/charts/echarts/HorizontalBarChart.js.map +1 -1
  26. package/dist/dts/components/facets/EnumFacet.d.ts +1 -1
  27. package/dist/dts/components/facets/EnumFacet.d.ts.map +1 -1
  28. package/dist/dts/components/facets/EnumFacet.js +6 -6
  29. package/dist/dts/components/facets/EnumFacet.js.map +1 -1
  30. package/dist/dts/components/facets/FacetEnumList.d.ts +2 -0
  31. package/dist/dts/components/facets/FacetEnumList.d.ts.map +1 -1
  32. package/dist/dts/components/facets/FacetEnumList.js +24 -18
  33. package/dist/dts/components/facets/FacetEnumList.js.map +1 -1
  34. package/dist/dts/components/facets/FacetSelectionModal.d.ts +1 -2
  35. package/dist/dts/components/facets/FacetSelectionModal.d.ts.map +1 -1
  36. package/dist/dts/components/facets/FacetSelectionModal.js.map +1 -1
  37. package/dist/dts/components/facets/FacetSelector.d.ts +1 -2
  38. package/dist/dts/components/facets/FacetSelector.d.ts.map +1 -1
  39. package/dist/dts/components/facets/FacetSelector.js +1 -1
  40. package/dist/dts/components/facets/FacetSelector.js.map +1 -1
  41. package/dist/dts/components/facets/FacetTabs.d.ts +1 -2
  42. package/dist/dts/components/facets/FacetTabs.d.ts.map +1 -1
  43. package/dist/dts/components/facets/FacetTabs.js.map +1 -1
  44. package/dist/dts/components/facets/FiltersPanel.d.ts +9 -0
  45. package/dist/dts/components/facets/FiltersPanel.d.ts.map +1 -0
  46. package/dist/dts/{features/CohortBuilder → components/facets}/FiltersPanel.js +3 -2
  47. package/dist/dts/components/facets/FiltersPanel.js.map +1 -0
  48. package/dist/dts/components/facets/Panels/AccordianPanel.d.ts.map +1 -0
  49. package/dist/dts/{features/CohortBuilder → components/facets}/Panels/AccordianPanel.js +1 -1
  50. package/dist/dts/components/facets/Panels/AccordianPanel.js.map +1 -0
  51. package/dist/dts/components/facets/Panels/DropdownPanel.d.ts.map +1 -0
  52. package/dist/dts/{features/CohortBuilder → components/facets}/Panels/DropdownPanel.js +3 -3
  53. package/dist/dts/components/facets/Panels/DropdownPanel.js.map +1 -0
  54. package/dist/dts/components/facets/Panels/TabbedPanel.d.ts +4 -0
  55. package/dist/dts/components/facets/Panels/TabbedPanel.d.ts.map +1 -0
  56. package/dist/dts/{features/CohortBuilder → components/facets}/Panels/TabbedPanel.js +3 -2
  57. package/dist/dts/components/facets/Panels/TabbedPanel.js.map +1 -0
  58. package/dist/dts/components/facets/Panels/index.d.ts +5 -0
  59. package/dist/dts/components/facets/Panels/index.d.ts.map +1 -0
  60. package/dist/dts/components/facets/Panels/index.js +5 -0
  61. package/dist/dts/components/facets/Panels/index.js.map +1 -0
  62. package/dist/dts/{features/CohortBuilder → components/facets}/Panels/types.d.ts +4 -3
  63. package/dist/dts/components/facets/Panels/types.d.ts.map +1 -0
  64. package/dist/dts/components/facets/Panels/types.js.map +1 -0
  65. package/dist/dts/components/facets/createFacetCard.d.ts +1 -2
  66. package/dist/dts/components/facets/createFacetCard.d.ts.map +1 -1
  67. package/dist/dts/components/facets/createFacetCard.js +4 -4
  68. package/dist/dts/components/facets/createFacetCard.js.map +1 -1
  69. package/dist/dts/components/facets/createFacetCards.d.ts +1 -2
  70. package/dist/dts/components/facets/createFacetCards.d.ts.map +1 -1
  71. package/dist/dts/components/facets/createFacetCards.js.map +1 -1
  72. package/dist/dts/components/facets/index.d.ts +6 -1
  73. package/dist/dts/components/facets/index.d.ts.map +1 -1
  74. package/dist/dts/components/facets/index.js +6 -1
  75. package/dist/dts/components/facets/index.js.map +1 -1
  76. package/dist/dts/components/facets/types.d.ts +17 -2
  77. package/dist/dts/components/facets/types.d.ts.map +1 -1
  78. package/dist/dts/components/facets/types.js.map +1 -1
  79. package/dist/dts/components/facets/utils.d.ts +2 -2
  80. package/dist/dts/components/facets/utils.d.ts.map +1 -1
  81. package/dist/dts/components/facets/utils.js +19 -1
  82. package/dist/dts/components/facets/utils.js.map +1 -1
  83. package/dist/dts/features/Analysis/AnalysisCard.d.ts.map +1 -1
  84. package/dist/dts/features/Analysis/AnalysisCard.js +1 -1
  85. package/dist/dts/features/Analysis/AnalysisCard.js.map +1 -1
  86. package/dist/dts/features/Analysis/AnalysisCard.stories.d.ts.map +1 -1
  87. package/dist/dts/features/Analysis/AnalysisCardCompact.stories.d.ts +10 -10
  88. package/dist/dts/features/Analysis/AnalysisCardCompact.stories.d.ts.map +1 -1
  89. package/dist/dts/features/Analysis/TextDescription.d.ts.map +1 -1
  90. package/dist/dts/features/Analysis/TextDescription.js +3 -19
  91. package/dist/dts/features/Analysis/TextDescription.js.map +1 -1
  92. package/dist/dts/features/CohortBuilder/CohortBuilder.d.ts.map +1 -1
  93. package/dist/dts/features/CohortBuilder/CohortBuilder.js +3 -13
  94. package/dist/dts/features/CohortBuilder/CohortBuilder.js.map +1 -1
  95. package/dist/dts/features/CohortBuilder/CohortManager/modals/SaveOrCreateEntityModal.js +1 -1
  96. package/dist/dts/features/CohortBuilder/CohortManager/modals/SaveOrCreateEntityModal.js.map +1 -1
  97. package/dist/dts/features/CohortBuilder/CohortPanel.d.ts.map +1 -1
  98. package/dist/dts/features/CohortBuilder/CohortPanel.js +29 -22
  99. package/dist/dts/features/CohortBuilder/CohortPanel.js.map +1 -1
  100. package/dist/dts/features/CohortBuilder/ExplorerTable/ArrayCellRenderer.d.ts +1 -1
  101. package/dist/dts/features/CohortBuilder/TabbedCohortBuilder.d.ts.map +1 -1
  102. package/dist/dts/features/CohortBuilder/TabbedCohortBuilder.js +16 -32
  103. package/dist/dts/features/CohortBuilder/TabbedCohortBuilder.js.map +1 -1
  104. package/dist/dts/features/CohortBuilder/types.d.ts +2 -2
  105. package/dist/dts/features/CohortBuilder/types.d.ts.map +1 -1
  106. package/dist/dts/features/CohortBuilder/types.js.map +1 -1
  107. package/dist/dts/features/CohortDiscovery/ChartsAndFacetsPanel.d.ts +2 -1
  108. package/dist/dts/features/CohortDiscovery/ChartsAndFacetsPanel.d.ts.map +1 -1
  109. package/dist/dts/features/CohortDiscovery/ChartsAndFacetsPanel.js.map +1 -1
  110. package/dist/dts/features/CohortDiscovery/CohortManagment/CohortManagerSelectors.d.ts +16 -16
  111. package/dist/dts/features/CohortDiscovery/FacetDefinitionsSlice.d.ts +1 -1
  112. package/dist/dts/features/CohortDiscovery/FacetDefinitionsSlice.d.ts.map +1 -1
  113. package/dist/dts/features/CohortDiscovery/FilterPanels/EnumFacetPanel.d.ts +1 -2
  114. package/dist/dts/features/CohortDiscovery/FilterPanels/EnumFacetPanel.d.ts.map +1 -1
  115. package/dist/dts/features/CohortDiscovery/FilterPanels/EnumFacetPanel.js.map +1 -1
  116. package/dist/dts/features/CohortDiscovery/FilterPanels/createFacetPanel.d.ts +2 -2
  117. package/dist/dts/features/CohortDiscovery/FilterPanels/createFacetPanel.d.ts.map +1 -1
  118. package/dist/dts/features/CohortDiscovery/FilterPanels/createFacetPanel.js.map +1 -1
  119. package/dist/dts/features/CohortDiscovery/RequestManagerSlice.d.ts +7 -7
  120. package/dist/dts/features/CohortDiscovery/appApi.d.ts +2 -2
  121. package/dist/dts/features/CohortDiscovery/registerApp.js +1 -1
  122. package/dist/dts/features/CohortDiscovery/registerApp.js.map +1 -1
  123. package/dist/dts/features/CohortSimilarity/cohortSimilarityApi.d.ts +10 -10
  124. package/dist/dts/features/Discovery/DataLoaders/MDSAllLocal/DataLoader.d.ts.map +1 -1
  125. package/dist/dts/features/Discovery/DataLoaders/MDSAllLocal/DataLoader.js +1 -0
  126. package/dist/dts/features/Discovery/DataLoaders/MDSAllLocal/DataLoader.js.map +1 -1
  127. package/dist/dts/features/Discovery/DiscoveryIndexPanel.d.ts.map +1 -1
  128. package/dist/dts/features/Discovery/DiscoveryIndexPanel.js +1 -1
  129. package/dist/dts/features/Discovery/DiscoveryIndexPanel.js.map +1 -1
  130. package/dist/dts/features/Discovery/DiscoveryTable.d.ts.map +1 -1
  131. package/dist/dts/features/Discovery/DiscoveryTable.js +30 -5
  132. package/dist/dts/features/Discovery/DiscoveryTable.js.map +1 -1
  133. package/dist/dts/features/Discovery/TableRenderers/CellRenderers.d.ts +1 -0
  134. package/dist/dts/features/Discovery/TableRenderers/CellRenderers.d.ts.map +1 -1
  135. package/dist/dts/features/Discovery/TableRenderers/CellRenderers.js +10 -0
  136. package/dist/dts/features/Discovery/TableRenderers/CellRenderers.js.map +1 -1
  137. package/dist/dts/features/Discovery/types.d.ts +7 -0
  138. package/dist/dts/features/Discovery/types.d.ts.map +1 -1
  139. package/dist/dts/features/Discovery/types.js.map +1 -1
  140. package/dist/dts/index.d.ts +3 -1
  141. package/dist/dts/index.d.ts.map +1 -1
  142. package/dist/dts/index.js +3 -1
  143. package/dist/dts/index.js.map +1 -1
  144. package/dist/esm/index.js +1217 -862
  145. package/dist/esm/index.js.map +1 -1
  146. package/dist/index.d.ts +295 -13
  147. package/dist/tsconfig.tsbuildinfo +1 -1
  148. package/package.json +3 -3
  149. package/dist/dts/api/staticNotebook/index.d.ts +0 -4
  150. package/dist/dts/api/staticNotebook/index.d.ts.map +0 -1
  151. package/dist/dts/api/staticNotebook/index.js +0 -118
  152. package/dist/dts/api/staticNotebook/index.js.map +0 -1
  153. package/dist/dts/api/staticNotebooks/index.d.ts +0 -4
  154. package/dist/dts/api/staticNotebooks/index.d.ts.map +0 -1
  155. package/dist/dts/api/staticNotebooks/index.js +0 -118
  156. package/dist/dts/api/staticNotebooks/index.js.map +0 -1
  157. package/dist/dts/features/CohortBuilder/FiltersPanel.d.ts +0 -10
  158. package/dist/dts/features/CohortBuilder/FiltersPanel.d.ts.map +0 -1
  159. package/dist/dts/features/CohortBuilder/FiltersPanel.js.map +0 -1
  160. package/dist/dts/features/CohortBuilder/Panels/AccordianPanel.d.ts.map +0 -1
  161. package/dist/dts/features/CohortBuilder/Panels/AccordianPanel.js.map +0 -1
  162. package/dist/dts/features/CohortBuilder/Panels/DropdownPanel.d.ts.map +0 -1
  163. package/dist/dts/features/CohortBuilder/Panels/DropdownPanel.js.map +0 -1
  164. package/dist/dts/features/CohortBuilder/Panels/TabbedPanel.d.ts +0 -3
  165. package/dist/dts/features/CohortBuilder/Panels/TabbedPanel.d.ts.map +0 -1
  166. package/dist/dts/features/CohortBuilder/Panels/TabbedPanel.js.map +0 -1
  167. package/dist/dts/features/CohortBuilder/Panels/types.d.ts.map +0 -1
  168. package/dist/dts/features/CohortBuilder/Panels/types.js.map +0 -1
  169. package/dist/dts/features/CohortDiscovery/CohortManager.d.ts +0 -6
  170. package/dist/dts/features/CohortDiscovery/CohortManager.d.ts.map +0 -1
  171. package/dist/dts/features/CohortDiscovery/CohortManager.js +0 -55
  172. package/dist/dts/features/CohortDiscovery/CohortManager.js.map +0 -1
  173. package/dist/dts/features/CohortDiscovery/CohortManagerSlice.d.ts +0 -135
  174. package/dist/dts/features/CohortDiscovery/CohortManagerSlice.d.ts.map +0 -1
  175. package/dist/dts/features/CohortDiscovery/CohortManagerSlice.js +0 -40
  176. package/dist/dts/features/CohortDiscovery/CohortManagerSlice.js.map +0 -1
  177. package/dist/dts/features/CohortDiscovery/SaveCohorts/SavedCohortsPanel.d.ts +0 -3
  178. package/dist/dts/features/CohortDiscovery/SaveCohorts/SavedCohortsPanel.d.ts.map +0 -1
  179. package/dist/dts/features/CohortDiscovery/SaveCohorts/SavedCohortsPanel.js +0 -9
  180. package/dist/dts/features/CohortDiscovery/SaveCohorts/SavedCohortsPanel.js.map +0 -1
  181. package/dist/dts/features/CohortDiscovery/SaveCohorts/SavedCohortsTable.d.ts +0 -7
  182. package/dist/dts/features/CohortDiscovery/SaveCohorts/SavedCohortsTable.d.ts.map +0 -1
  183. package/dist/dts/features/CohortDiscovery/SaveCohorts/SavedCohortsTable.js +0 -101
  184. package/dist/dts/features/CohortDiscovery/SaveCohorts/SavedCohortsTable.js.map +0 -1
  185. package/dist/dts/features/CohortDiscovery/appApiRTKQ.d.ts +0 -1
  186. package/dist/dts/features/CohortDiscovery/appApiRTKQ.d.ts.map +0 -1
  187. package/dist/dts/features/CohortDiscovery/appApiRTKQ.js +0 -101
  188. package/dist/dts/features/CohortDiscovery/appApiRTKQ.js.map +0 -1
  189. package/dist/dts/features/Discovery/Charts/ChartsPanel.d.ts +0 -9
  190. package/dist/dts/features/Discovery/Charts/ChartsPanel.d.ts.map +0 -1
  191. package/dist/dts/features/Discovery/Charts/ChartsPanel.js +0 -24
  192. package/dist/dts/features/Discovery/Charts/ChartsPanel.js.map +0 -1
  193. package/dist/dts/features/Discovery/Charts/CollapsableChartsPanel.d.ts +0 -9
  194. package/dist/dts/features/Discovery/Charts/CollapsableChartsPanel.d.ts.map +0 -1
  195. package/dist/dts/features/Discovery/Charts/CollapsableChartsPanel.js +0 -24
  196. package/dist/dts/features/Discovery/Charts/CollapsableChartsPanel.js.map +0 -1
  197. package/dist/dts/features/Discovery/StudyDetails/DetailsAuthorizationIcon.d.ts +0 -9
  198. package/dist/dts/features/Discovery/StudyDetails/DetailsAuthorizationIcon.d.ts.map +0 -1
  199. package/dist/dts/features/Discovery/StudyDetails/DetailsAuthorizationIcon.js +0 -12
  200. package/dist/dts/features/Discovery/StudyDetails/DetailsAuthorizationIcon.js.map +0 -1
  201. package/dist/dts/features/Discovery/StudyDetails/RendererFactory.d.ts +0 -19
  202. package/dist/dts/features/Discovery/StudyDetails/RendererFactory.d.ts.map +0 -1
  203. package/dist/dts/features/Discovery/StudyDetails/RendererFactory.js +0 -56
  204. package/dist/dts/features/Discovery/StudyDetails/RendererFactory.js.map +0 -1
  205. package/dist/dts/features/Discovery/StudyDetails/SinglePageStudyDetailsPanel.d.ts +0 -14
  206. package/dist/dts/features/Discovery/StudyDetails/SinglePageStudyDetailsPanel.d.ts.map +0 -1
  207. package/dist/dts/features/Discovery/StudyDetails/SinglePageStudyDetailsPanel.js +0 -44
  208. package/dist/dts/features/Discovery/StudyDetails/SinglePageStudyDetailsPanel.js.map +0 -1
  209. package/dist/dts/features/Discovery/StudyDetails/StudyDetails.d.ts +0 -3
  210. package/dist/dts/features/Discovery/StudyDetails/StudyDetails.d.ts.map +0 -1
  211. package/dist/dts/features/Discovery/StudyDetails/StudyDetails.js +0 -37
  212. package/dist/dts/features/Discovery/StudyDetails/StudyDetails.js.map +0 -1
  213. package/dist/dts/features/Discovery/StudyDetails/StudyDetailsPanel.d.ts +0 -10
  214. package/dist/dts/features/Discovery/StudyDetails/StudyDetailsPanel.d.ts.map +0 -1
  215. package/dist/dts/features/Discovery/StudyDetails/StudyDetailsPanel.js +0 -19
  216. package/dist/dts/features/Discovery/StudyDetails/StudyDetailsPanel.js.map +0 -1
  217. package/dist/dts/features/Discovery/StudyDetails/StudyGroup.d.ts +0 -8
  218. package/dist/dts/features/Discovery/StudyDetails/StudyGroup.d.ts.map +0 -1
  219. package/dist/dts/features/Discovery/StudyDetails/StudyGroup.js +0 -31
  220. package/dist/dts/features/Discovery/StudyDetails/StudyGroup.js.map +0 -1
  221. package/dist/dts/features/Discovery/StudyDetails/StudyGroupPanel.d.ts +0 -9
  222. package/dist/dts/features/Discovery/StudyDetails/StudyGroupPanel.d.ts.map +0 -1
  223. package/dist/dts/features/Discovery/StudyDetails/StudyGroupPanel.js +0 -11
  224. package/dist/dts/features/Discovery/StudyDetails/StudyGroupPanel.js.map +0 -1
  225. package/dist/dts/features/Discovery/StudyDetails/StudyItems.d.ts +0 -5
  226. package/dist/dts/features/Discovery/StudyDetails/StudyItems.d.ts.map +0 -1
  227. package/dist/dts/features/Discovery/StudyDetails/StudyItems.js +0 -283
  228. package/dist/dts/features/Discovery/StudyDetails/StudyItems.js.map +0 -1
  229. package/dist/dts/features/Discovery/StudyPage/DownloadLinksPanel.d.ts +0 -10
  230. package/dist/dts/features/Discovery/StudyPage/DownloadLinksPanel.d.ts.map +0 -1
  231. package/dist/dts/features/Discovery/StudyPage/DownloadLinksPanel.js +0 -45
  232. package/dist/dts/features/Discovery/StudyPage/DownloadLinksPanel.js.map +0 -1
  233. package/dist/dts/features/Discovery/StudyPage/StudyPage.d.ts +0 -10
  234. package/dist/dts/features/Discovery/StudyPage/StudyPage.d.ts.map +0 -1
  235. package/dist/dts/features/Discovery/StudyPage/StudyPage.js +0 -11
  236. package/dist/dts/features/Discovery/StudyPage/StudyPage.js.map +0 -1
  237. package/dist/dts/features/Discovery/StudyPage/StudyPageGroup.d.ts +0 -9
  238. package/dist/dts/features/Discovery/StudyPage/StudyPageGroup.d.ts.map +0 -1
  239. package/dist/dts/features/Discovery/StudyPage/StudyPageGroup.js +0 -8
  240. package/dist/dts/features/Discovery/StudyPage/StudyPageGroup.js.map +0 -1
  241. package/dist/dts/features/StaticNotebook/StaticNotebook.d.ts +0 -4
  242. package/dist/dts/features/StaticNotebook/StaticNotebook.d.ts.map +0 -1
  243. package/dist/dts/features/StaticNotebook/StaticNotebook.js +0 -79
  244. package/dist/dts/features/StaticNotebook/StaticNotebook.js.map +0 -1
  245. package/dist/dts/lib/notebooks/index.d.ts +0 -3
  246. package/dist/dts/lib/notebooks/index.d.ts.map +0 -1
  247. package/dist/dts/lib/notebooks/index.js +0 -96
  248. package/dist/dts/lib/notebooks/index.js.map +0 -1
  249. /package/dist/dts/{features/CohortBuilder → components/facets}/Panels/AccordianPanel.d.ts +0 -0
  250. /package/dist/dts/{features/CohortBuilder → components/facets}/Panels/DropdownPanel.d.ts +0 -0
  251. /package/dist/dts/{features/CohortBuilder → components/facets}/Panels/types.js +0 -0
package/dist/cjs/index.js CHANGED
@@ -26,10 +26,12 @@ var defaultComposer = require('default-composer');
26
26
  var react = require('@iconify-icon/react');
27
27
  var echarts = require('echarts');
28
28
  var victory = require('victory');
29
- var fa = require('react-icons/fa');
30
29
  var tw = require('tailwind-styled-components');
30
+ var form = require('@mantine/form');
31
31
  var ri = require('react-icons/ri');
32
+ var fa = require('react-icons/fa');
32
33
  var pi = require('react-icons/pi');
34
+ var modals = require('@mantine/modals');
33
35
  var Image = require('next/image');
34
36
  var Link = require('next/link');
35
37
  var ai = require('react-icons/ai');
@@ -45,7 +47,6 @@ var uniq = require('lodash/uniq');
45
47
  var sum = require('lodash/sum');
46
48
  var lu = require('react-icons/lu');
47
49
  require('universal-cookie');
48
- var modals = require('@mantine/modals');
49
50
  var GraphiQL = require('graphiql');
50
51
  var router$1 = require('next/dist/client/router');
51
52
  var fs = require('fs');
@@ -56,7 +57,6 @@ var redux = require('redux');
56
57
  var toolkit = require('@reduxjs/toolkit');
57
58
  var idb = require('idb');
58
59
  var createWebStorage = require('redux-persist/lib/storage/createWebStorage');
59
- var form = require('@mantine/form');
60
60
  var dynamic = require('next/dynamic');
61
61
  var YAML = require('yaml');
62
62
  var filesize = require('filesize');
@@ -1480,7 +1480,7 @@ function hashCode(str) {
1480
1480
  dangerouslySetInnerHTML: {
1481
1481
  __html: textString
1482
1482
  },
1483
- "aria-label": "HTML content" // Provide context for HTML rendered content
1483
+ "aria-label": "HTML content"
1484
1484
  });
1485
1485
  }
1486
1486
  case "textArray":
@@ -1620,7 +1620,7 @@ function hashCode(str) {
1620
1620
  * @param {string} paramValue - The parameter value
1621
1621
  * @returns {string} - The URL with the added parameter
1622
1622
  */ const appendParameterToUrl = (url, paramName, paramValue)=>{
1623
- if (!url || false) {
1623
+ if (!url || !paramName) {
1624
1624
  return url;
1625
1625
  }
1626
1626
  // Extract hash fragment if present
@@ -1956,8 +1956,7 @@ const saveToFile = (savingStr, filename = 'credentials.json')=>{
1956
1956
  children: [
1957
1957
  credentials.api_key === '' && /*#__PURE__*/ jsxRuntime.jsx(core$1.LoadingOverlay, {
1958
1958
  visible: true
1959
- }) // pragma: allowlist-secret;
1960
- ,
1959
+ }),
1961
1960
  /*#__PURE__*/ jsxRuntime.jsx("p", {
1962
1961
  children: "This key is only shown once. Please copy or save it and store it in a safe place."
1963
1962
  }),
@@ -2514,7 +2513,7 @@ const processChartData$2 = (facetData, valueType = 'count', total, maxBins = 100
2514
2513
  };
2515
2514
  const HorizontalBarChart = ({ data, valueType, total, showLegendInChart = true })=>{
2516
2515
  const chartData = processChartData$2(data, valueType, total);
2517
- const chartDefinition = React.useMemo(()=>{
2516
+ const chartDefinition = useDeepCompare.useDeepCompareMemo(()=>{
2518
2517
  return {
2519
2518
  tooltip: {
2520
2519
  trigger: 'item',
@@ -2556,12 +2555,17 @@ const HorizontalBarChart = ({ data, valueType, total, showLegendInChart = true }
2556
2555
  series: chartData
2557
2556
  };
2558
2557
  }, [
2559
- chartData
2558
+ chartData,
2559
+ showLegendInChart
2560
2560
  ]);
2561
2561
  return /*#__PURE__*/ jsxRuntime.jsx("div", {
2562
2562
  className: "w-full h-64",
2563
2563
  children: /*#__PURE__*/ jsxRuntime.jsx(ReactECharts, {
2564
- option: chartDefinition
2564
+ option: chartDefinition,
2565
+ settings: {
2566
+ notMerge: true,
2567
+ lazyUpdate: false
2568
+ }
2565
2569
  })
2566
2570
  });
2567
2571
  };
@@ -2589,7 +2593,11 @@ const ChartRendererFactory = ()=>{
2589
2593
  // TODO: add default chart chart for missing chart type
2590
2594
  const element = ChartRendererFactory().getRenderer('chart', type);
2591
2595
  return element({
2592
- ...chartProps
2596
+ total: chartProps.total,
2597
+ valueType: chartProps.valueType,
2598
+ label: chartProps.label,
2599
+ data: chartProps.data,
2600
+ showLegendInChart: chartProps.showLegendInChart
2593
2601
  }, parameters);
2594
2602
  };
2595
2603
 
@@ -2607,6 +2615,106 @@ const chartColors = [
2607
2615
  '#9a60b4',
2608
2616
  '#ea7ccc'
2609
2617
  ];
2618
+ const LegendRows = ({ data })=>{
2619
+ const moreThanMaxRows = data.length > MAX_LEGEND_ROWS;
2620
+ const limitedRows = moreThanMaxRows ? data.slice(0, MAX_LEGEND_ROWS) : data;
2621
+ return limitedRows.map((element, elIndex)=>/*#__PURE__*/ jsxRuntime.jsxs(core$1.Table.Tr, {
2622
+ children: [
2623
+ /*#__PURE__*/ jsxRuntime.jsxs(core$1.Table.Td, {
2624
+ children: [
2625
+ /*#__PURE__*/ jsxRuntime.jsx(core$1.ColorSwatch, {
2626
+ className: "inline-block mr-2 align-middle",
2627
+ size: "1em",
2628
+ radius: "xs",
2629
+ color: chartColors?.[elIndex % chartColors.length] || ''
2630
+ }),
2631
+ element.key
2632
+ ]
2633
+ }),
2634
+ /*#__PURE__*/ jsxRuntime.jsx(core$1.Table.Td, {
2635
+ className: "text-right",
2636
+ children: element.count
2637
+ })
2638
+ ]
2639
+ }, elIndex));
2640
+ };
2641
+ const LegendOverflow = ({ chart, data, chartTitle, counts })=>{
2642
+ const [openedMoreRows, { open: openMoreRows, close: closeMoreRows }] = hooks.useDisclosure(false);
2643
+ const theme = core$1.useMantineTheme();
2644
+ return /*#__PURE__*/ jsxRuntime.jsxs(React.Fragment, {
2645
+ children: [
2646
+ /*#__PURE__*/ jsxRuntime.jsx(core$1.Modal, {
2647
+ opened: openedMoreRows,
2648
+ onClose: closeMoreRows,
2649
+ title: chartTitle,
2650
+ size: "xl",
2651
+ children: /*#__PURE__*/ jsxRuntime.jsxs(core$1.Grid, {
2652
+ children: [
2653
+ /*#__PURE__*/ jsxRuntime.jsx(core$1.Grid.Col, {
2654
+ span: 6,
2655
+ children: createChart(chart.chartType, {
2656
+ data: data === undefined ? [] : data,
2657
+ total: counts ?? 1,
2658
+ valueType: chart.valueType ?? 'count',
2659
+ label: chart.label,
2660
+ showLegendInChart: chart.showLegendInChart
2661
+ })
2662
+ }, "modal-col-1"),
2663
+ /*#__PURE__*/ jsxRuntime.jsx(core$1.Grid.Col, {
2664
+ span: 6,
2665
+ children: /*#__PURE__*/ jsxRuntime.jsx("div", {
2666
+ className: "border-solid border-[1px] border-[var(--mantine-color-gray-3)] h-full p-1",
2667
+ children: /*#__PURE__*/ jsxRuntime.jsx(core$1.Table, {
2668
+ withRowBorders: false,
2669
+ classNames: {
2670
+ table: '',
2671
+ td: 'p-1 leading-3'
2672
+ },
2673
+ children: /*#__PURE__*/ jsxRuntime.jsx(core$1.Table.Tbody, {
2674
+ children: data.map((element, elIndex)=>/*#__PURE__*/ jsxRuntime.jsxs(core$1.Table.Tr, {
2675
+ children: [
2676
+ /*#__PURE__*/ jsxRuntime.jsxs(core$1.Table.Td, {
2677
+ children: [
2678
+ /*#__PURE__*/ jsxRuntime.jsx(core$1.ColorSwatch, {
2679
+ className: "inline-block mr-2 align-middle",
2680
+ size: "1em",
2681
+ radius: "xs",
2682
+ color: chartColors?.[elIndex % chartColors.length] || ''
2683
+ }),
2684
+ element.key
2685
+ ]
2686
+ }),
2687
+ /*#__PURE__*/ jsxRuntime.jsx(core$1.Table.Td, {
2688
+ className: "text-right",
2689
+ children: element.count
2690
+ })
2691
+ ]
2692
+ }, elIndex))
2693
+ })
2694
+ })
2695
+ })
2696
+ }, "modal-col-2")
2697
+ ]
2698
+ })
2699
+ }),
2700
+ /*#__PURE__*/ jsxRuntime.jsxs(core$1.Button, {
2701
+ variant: "subtle",
2702
+ onClick: openMoreRows,
2703
+ leftSection: /*#__PURE__*/ jsxRuntime.jsx(react.Icon, {
2704
+ icon: "gen3:open-in-modal",
2705
+ height: 24,
2706
+ width: 24,
2707
+ color: theme.colors.accent[5]
2708
+ }),
2709
+ className: "text-black hover:text-black",
2710
+ children: [
2711
+ data.length - MAX_LEGEND_ROWS,
2712
+ " more"
2713
+ ]
2714
+ })
2715
+ ]
2716
+ });
2717
+ };
2610
2718
  //The Charts component maps the data from ChartsProps into a grid of createChart() ReactNodes
2611
2719
  const Charts = ({ charts, data, counts, isSuccess, numCols = DEFAULT_COLS, style = 'tile', showLegends = false })=>{
2612
2720
  const spans = computeRowSpan(Object.keys(charts).length, numCols);
@@ -2617,109 +2725,10 @@ const Charts = ({ charts, data, counts, isSuccess, numCols = DEFAULT_COLS, style
2617
2725
  message: `${field} not found in data`
2618
2726
  });
2619
2727
  }
2620
- const LegendRows = ({ data })=>{
2621
- const moreThanMaxRows = data.length > MAX_LEGEND_ROWS;
2622
- const limitedRows = moreThanMaxRows ? data.slice(0, MAX_LEGEND_ROWS) : data;
2623
- return limitedRows.map((element, elIndex)=>/*#__PURE__*/ jsxRuntime.jsxs(core$1.Table.Tr, {
2624
- children: [
2625
- /*#__PURE__*/ jsxRuntime.jsxs(core$1.Table.Td, {
2626
- children: [
2627
- /*#__PURE__*/ jsxRuntime.jsx(core$1.ColorSwatch, {
2628
- className: "inline-block mr-2 align-middle",
2629
- size: "1em",
2630
- radius: "xs",
2631
- color: chartColors?.[elIndex % chartColors.length] || ''
2632
- }),
2633
- element.key
2634
- ]
2635
- }),
2636
- /*#__PURE__*/ jsxRuntime.jsx(core$1.Table.Td, {
2637
- className: "text-right",
2638
- children: element.count
2639
- })
2640
- ]
2641
- }, elIndex));
2642
- };
2643
- const LegendOverflow = ({ chart, data, chartTitle })=>{
2644
- const [openedMoreRows, { open: openMoreRows, close: closeMoreRows }] = hooks.useDisclosure(false);
2645
- const theme = core$1.useMantineTheme();
2646
- return /*#__PURE__*/ jsxRuntime.jsxs(React.Fragment, {
2647
- children: [
2648
- /*#__PURE__*/ jsxRuntime.jsx(core$1.Modal, {
2649
- opened: openedMoreRows,
2650
- onClose: closeMoreRows,
2651
- title: chartTitle,
2652
- size: "xl",
2653
- children: /*#__PURE__*/ jsxRuntime.jsxs(core$1.Grid, {
2654
- children: [
2655
- /*#__PURE__*/ jsxRuntime.jsx(core$1.Grid.Col, {
2656
- span: 6,
2657
- children: createChart(chart.chartType, {
2658
- data: data === undefined ? [] : data,
2659
- total: counts ?? 1,
2660
- valueType: chart.valueType ?? 'count',
2661
- label: chart.label,
2662
- showLegendInChart: chart.showLegendInChart
2663
- })
2664
- }, "modal-col-1"),
2665
- /*#__PURE__*/ jsxRuntime.jsx(core$1.Grid.Col, {
2666
- span: 6,
2667
- children: /*#__PURE__*/ jsxRuntime.jsx("div", {
2668
- className: "border-solid border-[1px] border-[var(--mantine-color-gray-3)] h-full p-1",
2669
- children: /*#__PURE__*/ jsxRuntime.jsx(core$1.Table, {
2670
- withRowBorders: false,
2671
- classNames: {
2672
- table: '',
2673
- td: 'p-1 leading-3'
2674
- },
2675
- children: /*#__PURE__*/ jsxRuntime.jsx(core$1.Table.Tbody, {
2676
- children: data.map((element, elIndex)=>/*#__PURE__*/ jsxRuntime.jsxs(core$1.Table.Tr, {
2677
- children: [
2678
- /*#__PURE__*/ jsxRuntime.jsxs(core$1.Table.Td, {
2679
- children: [
2680
- /*#__PURE__*/ jsxRuntime.jsx(core$1.ColorSwatch, {
2681
- className: "inline-block mr-2 align-middle",
2682
- size: "1em",
2683
- radius: "xs",
2684
- color: chartColors?.[elIndex % chartColors.length] || ''
2685
- }),
2686
- element.key
2687
- ]
2688
- }),
2689
- /*#__PURE__*/ jsxRuntime.jsx(core$1.Table.Td, {
2690
- className: "text-right",
2691
- children: element.count
2692
- })
2693
- ]
2694
- }, elIndex))
2695
- })
2696
- })
2697
- })
2698
- }, "modal-col-2")
2699
- ]
2700
- })
2701
- }),
2702
- /*#__PURE__*/ jsxRuntime.jsxs(core$1.Button, {
2703
- variant: "subtle",
2704
- onClick: openMoreRows,
2705
- leftSection: /*#__PURE__*/ jsxRuntime.jsx(react.Icon, {
2706
- icon: "gen3:open-in-modal",
2707
- height: 24,
2708
- width: 24,
2709
- color: theme.colors.accent[5]
2710
- }),
2711
- className: "text-black hover:text-black",
2712
- children: [
2713
- data.length - MAX_LEGEND_ROWS,
2714
- " more"
2715
- ]
2716
- })
2717
- ]
2718
- });
2719
- };
2720
2728
  const dataKeys = field in data && data?.[field].length > 0 ? Object.keys(data[field][0]) : [];
2721
2729
  const chartTitle = charts[field].title ?? core.fieldNameToTitle(field);
2722
- const moreThanMaxRows = data?.[field] && data[field].length > MAX_LEGEND_ROWS;
2730
+ const numberOfDataItems = data?.[field] && data[field].length;
2731
+ const moreThanMaxRows = numberOfDataItems > MAX_LEGEND_ROWS;
2723
2732
  return /*#__PURE__*/ jsxRuntime.jsx(core$1.Grid.Col, {
2724
2733
  span: spans[indexNum],
2725
2734
  children: /*#__PURE__*/ jsxRuntime.jsxs(core$1.Card, {
@@ -2750,7 +2759,7 @@ const Charts = ({ charts, data, counts, isSuccess, numCols = DEFAULT_COLS, style
2750
2759
  label: charts[field].label,
2751
2760
  showLegendInChart: charts[field].showLegendInChart
2752
2761
  }),
2753
- showLegends && /*#__PURE__*/ jsxRuntime.jsx(core$1.Card.Section, {
2762
+ numberOfDataItems > 0 && showLegends && /*#__PURE__*/ jsxRuntime.jsx(core$1.Card.Section, {
2754
2763
  inheritPadding: true,
2755
2764
  py: "xs",
2756
2765
  withBorder: style === 'box',
@@ -2788,7 +2797,8 @@ const Charts = ({ charts, data, counts, isSuccess, numCols = DEFAULT_COLS, style
2788
2797
  children: /*#__PURE__*/ jsxRuntime.jsx(LegendOverflow, {
2789
2798
  chart: charts[field],
2790
2799
  data: data[field],
2791
- chartTitle: chartTitle
2800
+ chartTitle: chartTitle,
2801
+ counts: counts ?? 0
2792
2802
  })
2793
2803
  })
2794
2804
  ]
@@ -2801,7 +2811,7 @@ const Charts = ({ charts, data, counts, isSuccess, numCols = DEFAULT_COLS, style
2801
2811
  });
2802
2812
  };
2803
2813
 
2804
- const CollapsableCharts = ({ config, data })=>{
2814
+ const CollapsableCharts = ({ config, data, isError, isFetching, isSuccess })=>{
2805
2815
  const [showLegends, setShowLegends] = React.useState(config.showLegends?.enabled);
2806
2816
  if (!(config?.charts && Object.keys(config.charts).length > 0)) {
2807
2817
  return /*#__PURE__*/ jsxRuntime.jsx(core$1.Center, {
@@ -2853,7 +2863,7 @@ const CollapsableCharts = ({ config, data })=>{
2853
2863
  charts: config.charts,
2854
2864
  data: data,
2855
2865
  counts: 2,
2856
- isSuccess: true,
2866
+ isSuccess: isSuccess,
2857
2867
  numCols: 4
2858
2868
  })
2859
2869
  })
@@ -3165,6 +3175,8 @@ const classifyFacets = (data, index, fieldMapping = [], facetDefinitionsFromConf
3165
3175
  label: facetDef.label ?? facetName,
3166
3176
  // assumption is that the initial data has the min and max values
3167
3177
  sharedWithIndices: (sharedFieldMapping && fieldKey in sharedFieldMapping && sharedFieldMapping[fieldKey].filter((x)=>x.index !== index)) ?? undefined,
3178
+ moveValuesToBottom: facetDef?.moveValuesToBottom,
3179
+ excludeValues: facetDef?.excludeValues,
3168
3180
  range: facetDef.range ?? type === 'range' ? {
3169
3181
  minimum: Math.floor(Number(value[0].key[0])),
3170
3182
  maximum: Math.ceil(Number(value[0].key[1]))
@@ -3343,6 +3355,22 @@ const convertToStringArray = (inputArray)=>inputArray.map(String);
3343
3355
  * @param {FacetSortType} facetSort - The facet sort type represented as a string in the format "type-direction".
3344
3356
  * @returns {SortType} - The mapped sort type object containing type and direction.
3345
3357
  */ const mapFacetSortToSortType = (facetSort)=>{
3358
+ // Default fallback values
3359
+ const defaultSort = {
3360
+ type: 'value',
3361
+ direction: 'dsc'
3362
+ };
3363
+ // Validate input
3364
+ if (!facetSort) {
3365
+ console.warn(`Invalid facetSort: expected string, got ${typeof facetSort}. Using default.`);
3366
+ return defaultSort;
3367
+ }
3368
+ const parts = facetSort.split('-');
3369
+ // Check if we have exactly 2 parts
3370
+ if (parts.length !== 2) {
3371
+ console.warn(`Invalid facetSort format: expected 'type-direction', got '${facetSort}'. Using default.`);
3372
+ return defaultSort;
3373
+ }
3346
3374
  const [type, direction] = facetSort.split('-');
3347
3375
  return {
3348
3376
  type: type === 'label' ? 'alpha' : 'value',
@@ -3417,6 +3445,173 @@ const DEFAULT_MAXIMUM = 100;
3417
3445
  const BAD_DATA_MESSAGE = 'No data for this field';
3418
3446
  const DAYS_IN_YEAR = 365.25;
3419
3447
 
3448
+ const SegmentedControl = (props)=>{
3449
+ return /*#__PURE__*/ jsxRuntime.jsx(core$1.SegmentedControl, {
3450
+ classNames: {
3451
+ root: 'bg-base-max h-fit p-0',
3452
+ indicator: 'opacity-0',
3453
+ control: 'z-0 rounded-none border-0 [&:nth-child(2)>label]:rounded-l-md [&:last-child>label]:rounded-r-md [&:last-child>label]:border-r-1',
3454
+ label: `${props?.padding ? `p-${props.padding}` : 'p-0'} text-primary font-semibold data-active:text-base-max data-active:bg-primary data-disabled:bg-base-lightest data-disabled:text-base-lighter
3455
+ border-1 border-r-0 !border-primary rounded-none data-disabled:!border-base-lighter`
3456
+ },
3457
+ ...props
3458
+ });
3459
+ };
3460
+
3461
+ const ExpanderLabel = tw.div`
3462
+ text-accent-content-darker
3463
+ p-1
3464
+ font-bold
3465
+ cursor-pointer
3466
+ text-xs
3467
+ font-content
3468
+ `;
3469
+ /**
3470
+ * Component which manages the compact/expanded state of a FacetCard
3471
+ * @param remainingValues - number of remaining values when compact "show 4"
3472
+ * @param isGroupExpanded - true if expanded, false if compact
3473
+ * @param onShowChanged - callback to call when the expand/compact button is clicked
3474
+ */ const FacetExpander = ({ remainingValues, isGroupExpanded, onShowChanged })=>{
3475
+ return /*#__PURE__*/ jsxRuntime.jsx("div", {
3476
+ className: `mt-3 flex flex-row justify-end ${remainingValues > 0 && 'border-t-2'} p-1.5`,
3477
+ children: remainingValues > 0 && !isGroupExpanded ? /*#__PURE__*/ jsxRuntime.jsx("button", {
3478
+ onClick: ()=>onShowChanged(!isGroupExpanded),
3479
+ "data-testid": "plus-icon",
3480
+ children: /*#__PURE__*/ jsxRuntime.jsxs("div", {
3481
+ className: "flex flex-row flex-nowrap items-center ",
3482
+ children: [
3483
+ /*#__PURE__*/ jsxRuntime.jsx(md.MdAddCircle, {
3484
+ className: "text-accent",
3485
+ size: "1rem",
3486
+ "aria-hidden": "true"
3487
+ }, "show-more"),
3488
+ /*#__PURE__*/ jsxRuntime.jsxs(ExpanderLabel, {
3489
+ children: [
3490
+ remainingValues,
3491
+ " more"
3492
+ ]
3493
+ })
3494
+ ]
3495
+ })
3496
+ }) : isGroupExpanded ? /*#__PURE__*/ jsxRuntime.jsx("button", {
3497
+ onClick: ()=>onShowChanged(!isGroupExpanded),
3498
+ "data-testid": "minus-icon",
3499
+ children: /*#__PURE__*/ jsxRuntime.jsxs("div", {
3500
+ className: "flex flex-row flex-nowrap items-center",
3501
+ children: [
3502
+ /*#__PURE__*/ jsxRuntime.jsx(md.MdRemoveCircle, {
3503
+ className: "text-accent",
3504
+ size: "1rem",
3505
+ onClick: ()=>onShowChanged(!isGroupExpanded),
3506
+ "aria-hidden": "true"
3507
+ }, "show-less"),
3508
+ /*#__PURE__*/ jsxRuntime.jsx(ExpanderLabel, {
3509
+ children: "show less"
3510
+ })
3511
+ ]
3512
+ })
3513
+ }) : null
3514
+ });
3515
+ };
3516
+
3517
+ const sortTypeToAriaDescription = (sortTypeAndDirection, valueLabel, field)=>{
3518
+ if (sortTypeAndDirection.type === 'alpha') {
3519
+ return sortTypeAndDirection.direction === 'asc' ? `The ${field} names are now sorted alphabetically ascending` : `The ${field} names are now sorted alphabetically descending`;
3520
+ } else {
3521
+ return sortTypeAndDirection.direction === 'asc' ? `The ${field} ${valueLabel} are now sorted numerically ascending` : `The ${field} ${valueLabel} are now sorted numerically descending`;
3522
+ }
3523
+ };
3524
+ /**
3525
+ * FacetCards "sort" header supporting sort by A-Z or by Value both ascending and descending
3526
+ * @param sortType - current sort type
3527
+ * @param valueLabel - Value labels, typically "case" "file"
3528
+ * @param setSort - sets the sort type and direction
3529
+ * @param field - specifies the facet table name
3530
+ */ const FacetSortPanel = ({ sortType, valueLabel, setSort, field })=>{
3531
+ const liveRegionRef = React.useRef(null);
3532
+ const [sortingStatus, setSortingStatus] = React.useState('');
3533
+ React.useEffect(()=>{
3534
+ if (sortingStatus && liveRegionRef?.current) {
3535
+ liveRegionRef.current.textContent = sortingStatus;
3536
+ }
3537
+ }, [
3538
+ sortingStatus
3539
+ ]);
3540
+ const [NameSortIcon, nameIconSize] = sortType.type === 'alpha' ? sortType.direction === 'asc' ? [
3541
+ pi.PiCaretUpFill,
3542
+ '0.75rem'
3543
+ ] : [
3544
+ pi.PiCaretDownFill,
3545
+ '0.75rem'
3546
+ ] : [
3547
+ pi.PiCaretUpDownFill,
3548
+ '1rem'
3549
+ ];
3550
+ const [ValueSortIcon, valueIconSize] = sortType.type === 'value' ? sortType.direction === 'asc' ? [
3551
+ pi.PiCaretUpFill,
3552
+ '0.75rem'
3553
+ ] : [
3554
+ pi.PiCaretDownFill,
3555
+ '0.75rem'
3556
+ ] : [
3557
+ pi.PiCaretUpDownFill,
3558
+ '1rem'
3559
+ ];
3560
+ return /*#__PURE__*/ jsxRuntime.jsxs("div", {
3561
+ className: "flex flex-row items-center justify-between flex-wrap py-1 px-2 mb-1 border-b-2",
3562
+ children: [
3563
+ /*#__PURE__*/ jsxRuntime.jsx(core$1.Button, {
3564
+ className: "pl-0 ml-0 api-hovered:accent",
3565
+ variant: "transparent",
3566
+ size: "compact-xs",
3567
+ color: "base-contrast.5",
3568
+ onClick: ()=>{
3569
+ const direction = sortType.type === 'alpha' && sortType.direction === 'asc' ? 'dsc' : 'asc';
3570
+ const sortObj = {
3571
+ type: 'alpha',
3572
+ direction
3573
+ };
3574
+ setSort(sortObj);
3575
+ setSortingStatus(sortTypeToAriaDescription(sortObj, 'Name', field));
3576
+ },
3577
+ rightSection: /*#__PURE__*/ jsxRuntime.jsx(NameSortIcon, {
3578
+ size: nameIconSize,
3579
+ "aria-hidden": "true"
3580
+ }),
3581
+ "aria-label": "Sort name alphabetically",
3582
+ children: "Name"
3583
+ }),
3584
+ /*#__PURE__*/ jsxRuntime.jsx(core$1.Button, {
3585
+ className: "pr-0 mr-0",
3586
+ variant: "transparent",
3587
+ size: "compact-xs",
3588
+ color: "base-contrast.5",
3589
+ onClick: ()=>{
3590
+ const direction = sortType.type === 'value' && sortType.direction === 'asc' ? 'dsc' : 'asc';
3591
+ const sortObj = {
3592
+ type: 'value',
3593
+ direction
3594
+ };
3595
+ setSort(sortObj);
3596
+ setSortingStatus(sortTypeToAriaDescription(sortObj, valueLabel, field));
3597
+ },
3598
+ rightSection: /*#__PURE__*/ jsxRuntime.jsx(ValueSortIcon, {
3599
+ size: valueIconSize,
3600
+ "aria-hidden": "true"
3601
+ }),
3602
+ "aria-label": `Sort ${valueLabel} numerically`,
3603
+ children: valueLabel
3604
+ }),
3605
+ /*#__PURE__*/ jsxRuntime.jsx("span", {
3606
+ id: `${field}-liveRegion`,
3607
+ "aria-live": "polite",
3608
+ ref: liveRegionRef,
3609
+ className: "sr-only"
3610
+ })
3611
+ ]
3612
+ });
3613
+ };
3614
+
3420
3615
  const FacetIconButton = tw.button`
3421
3616
  text-base-max
3422
3617
  font-bold
@@ -3623,104 +3818,6 @@ flex items-start justify-between items-center flex-nowrap bg-secondary px-1.5 ro
3623
3818
  });
3624
3819
  };
3625
3820
 
3626
- const sortTypeToAriaDescription = (sortTypeAndDirection, valueLabel, field)=>{
3627
- if (sortTypeAndDirection.type === 'alpha') {
3628
- return sortTypeAndDirection.direction === 'asc' ? `The ${field} names are now sorted alphabetically ascending` : `The ${field} names are now sorted alphabetically descending`;
3629
- } else {
3630
- return sortTypeAndDirection.direction === 'asc' ? `The ${field} ${valueLabel} are now sorted numerically ascending` : `The ${field} ${valueLabel} are now sorted numerically descending`;
3631
- }
3632
- };
3633
- /**
3634
- * FacetCards "sort" header supporting sort by A-Z or by Value both ascending and descending
3635
- * @param sortType - current sort type
3636
- * @param valueLabel - Value labels, typically "case" "file"
3637
- * @param setSort - sets the sort type and direction
3638
- * @param field - specifies the facet table name
3639
- */ const FacetSortPanel = ({ sortType, valueLabel, setSort, field })=>{
3640
- const liveRegionRef = React.useRef(null);
3641
- const [sortingStatus, setSortingStatus] = React.useState('');
3642
- React.useEffect(()=>{
3643
- if (sortingStatus && liveRegionRef?.current) {
3644
- liveRegionRef.current.textContent = sortingStatus;
3645
- }
3646
- }, [
3647
- sortingStatus
3648
- ]);
3649
- const [NameSortIcon, nameIconSize] = sortType.type === 'alpha' ? sortType.direction === 'asc' ? [
3650
- pi.PiCaretUpFill,
3651
- '0.75rem'
3652
- ] : [
3653
- pi.PiCaretDownFill,
3654
- '0.75rem'
3655
- ] : [
3656
- pi.PiCaretUpDownFill,
3657
- '1rem'
3658
- ];
3659
- const [ValueSortIcon, valueIconSize] = sortType.type === 'value' ? sortType.direction === 'asc' ? [
3660
- pi.PiCaretUpFill,
3661
- '0.75rem'
3662
- ] : [
3663
- pi.PiCaretDownFill,
3664
- '0.75rem'
3665
- ] : [
3666
- pi.PiCaretUpDownFill,
3667
- '1rem'
3668
- ];
3669
- return /*#__PURE__*/ jsxRuntime.jsxs("div", {
3670
- className: "flex flex-row items-center justify-between flex-wrap py-1 px-2 mb-1 border-b-2",
3671
- children: [
3672
- /*#__PURE__*/ jsxRuntime.jsx(core$1.Button, {
3673
- className: "pl-0 ml-0 api-hovered:accent",
3674
- variant: "transparent",
3675
- size: "compact-xs",
3676
- color: "base-contrast.5",
3677
- onClick: ()=>{
3678
- const direction = sortType.type === 'alpha' && sortType.direction === 'asc' ? 'dsc' : 'asc';
3679
- const sortObj = {
3680
- type: 'alpha',
3681
- direction
3682
- };
3683
- setSort(sortObj);
3684
- setSortingStatus(sortTypeToAriaDescription(sortObj, 'Name', field));
3685
- },
3686
- rightSection: /*#__PURE__*/ jsxRuntime.jsx(NameSortIcon, {
3687
- size: nameIconSize,
3688
- "aria-hidden": "true"
3689
- }),
3690
- "aria-label": "Sort name alphabetically",
3691
- children: "Name"
3692
- }),
3693
- /*#__PURE__*/ jsxRuntime.jsx(core$1.Button, {
3694
- className: "pr-0 mr-0",
3695
- variant: "transparent",
3696
- size: "compact-xs",
3697
- color: "base-contrast.5",
3698
- onClick: ()=>{
3699
- const direction = sortType.type === 'value' && sortType.direction === 'asc' ? 'dsc' : 'asc';
3700
- const sortObj = {
3701
- type: 'value',
3702
- direction
3703
- };
3704
- setSort(sortObj);
3705
- setSortingStatus(sortTypeToAriaDescription(sortObj, valueLabel, field));
3706
- },
3707
- rightSection: /*#__PURE__*/ jsxRuntime.jsx(ValueSortIcon, {
3708
- size: valueIconSize,
3709
- "aria-hidden": "true"
3710
- }),
3711
- "aria-label": `Sort ${valueLabel} numerically`,
3712
- children: valueLabel
3713
- }),
3714
- /*#__PURE__*/ jsxRuntime.jsx("span", {
3715
- id: `${field}-liveRegion`,
3716
- "aria-live": "polite",
3717
- ref: liveRegionRef,
3718
- className: "sr-only"
3719
- })
3720
- ]
3721
- });
3722
- };
3723
-
3724
3821
  const OverflowTooltippedLabel = ({ children, label, className = 'flex-grow font-heading text-md pt-0.5' })=>{
3725
3822
  const [showTooltip, setShowTooltip] = React.useState(false);
3726
3823
  return /*#__PURE__*/ jsxRuntime.jsx(core$1.Tooltip, {
@@ -3751,63 +3848,7 @@ const OverflowTooltippedLabel = ({ children, label, className = 'flex-grow font-
3751
3848
  });
3752
3849
  };
3753
3850
 
3754
- const ExpanderLabel = tw.div`
3755
- text-accent-content-darker
3756
- p-1
3757
- font-bold
3758
- cursor-pointer
3759
- text-xs
3760
- font-content
3761
- `;
3762
- /**
3763
- * Component which manages the compact/expanded state of a FacetCard
3764
- * @param remainingValues - number of remaining values when compact "show 4"
3765
- * @param isGroupExpanded - true if expanded, false if compact
3766
- * @param onShowChanged - callback to call when the expand/compact button is clicked
3767
- */ const FacetExpander = ({ remainingValues, isGroupExpanded, onShowChanged })=>{
3768
- return /*#__PURE__*/ jsxRuntime.jsx("div", {
3769
- className: `mt-3 flex flex-row justify-end ${remainingValues > 0 && 'border-t-2'} p-1.5`,
3770
- children: remainingValues > 0 && !isGroupExpanded ? /*#__PURE__*/ jsxRuntime.jsx("button", {
3771
- onClick: ()=>onShowChanged(!isGroupExpanded),
3772
- "data-testid": "plus-icon",
3773
- children: /*#__PURE__*/ jsxRuntime.jsxs("div", {
3774
- className: "flex flex-row flex-nowrap items-center ",
3775
- children: [
3776
- /*#__PURE__*/ jsxRuntime.jsx(md.MdAddCircle, {
3777
- className: "text-accent",
3778
- size: "1rem",
3779
- "aria-hidden": "true"
3780
- }, "show-more"),
3781
- /*#__PURE__*/ jsxRuntime.jsxs(ExpanderLabel, {
3782
- children: [
3783
- remainingValues,
3784
- " more"
3785
- ]
3786
- })
3787
- ]
3788
- })
3789
- }) : isGroupExpanded ? /*#__PURE__*/ jsxRuntime.jsx("button", {
3790
- onClick: ()=>onShowChanged(!isGroupExpanded),
3791
- "data-testid": "minus-icon",
3792
- children: /*#__PURE__*/ jsxRuntime.jsxs("div", {
3793
- className: "flex flex-row flex-nowrap items-center",
3794
- children: [
3795
- /*#__PURE__*/ jsxRuntime.jsx(md.MdRemoveCircle, {
3796
- className: "text-accent",
3797
- size: "1rem",
3798
- onClick: ()=>onShowChanged(!isGroupExpanded),
3799
- "aria-hidden": "true"
3800
- }, "show-less"),
3801
- /*#__PURE__*/ jsxRuntime.jsx(ExpanderLabel, {
3802
- children: "show less"
3803
- })
3804
- ]
3805
- })
3806
- }) : null
3807
- });
3808
- };
3809
-
3810
- const FacetEnumList = ({ field, facetName, hooks, valueLabel, isSettings = false, isFacetView = true, isSearching = false, showPercent = false, hideIfEmpty = false, showSorting = true, sort = 'value-dsc' })=>{
3851
+ const FacetEnumList = ({ field, facetName, hooks, valueLabel, isSettings = false, isFacetView = true, isSearching = false, showPercent = false, hideIfEmpty = false, showSorting = true, sort = 'value-dsc', moveValuesToBottom = [], excludeValues = [] })=>{
3811
3852
  const [isGroupExpanded, setIsGroupExpanded] = React.useState(false);
3812
3853
  const cardRef = React.useRef(null);
3813
3854
  const searchInputRef = React.useRef(null);
@@ -3864,7 +3905,7 @@ const FacetEnumList = ({ field, facetName, hooks, valueLabel, isSettings = false
3864
3905
  ];
3865
3906
  updateFacetEnum(field, updated, updateFacetFilters, clearFilters, combineMode);
3866
3907
  } else {
3867
- const updated = selectedEnums?.filter((x)=>x != value);
3908
+ const updated = selectedEnums?.filter((x)=>x !== value);
3868
3909
  updateFacetEnum(field, updated ?? [], updateFacetFilters, clearFilters, combineMode);
3869
3910
  }
3870
3911
  };
@@ -3901,7 +3942,7 @@ const FacetEnumList = ({ field, facetName, hooks, valueLabel, isSettings = false
3901
3942
  useDeepCompare.useDeepCompareEffect(()=>{
3902
3943
  if (isSuccess && data) {
3903
3944
  // get all the data except the missing and empty values
3904
- const tempFilteredData = Object.entries(data).filter((entry)=>entry[0] != '_missing' && entry[0] != '').filter((entry)=>searchTerm === '' ? entry : entry[0].toLowerCase().includes(searchTerm.toLowerCase().trim()));
3945
+ const tempFilteredData = Object.entries(data).filter((entry)=>entry[0] !== '_missing' && entry[0] !== '').filter((entry)=>searchTerm === '' ? entry : entry[0].toLowerCase().includes(searchTerm.toLowerCase().trim()));
3905
3946
  // it is possible that the selected enums are not in the data as their counts are 0
3906
3947
  // therefore we need to add them to the data
3907
3948
  const selectedEnumNotInData = selectedEnums ? selectedEnums.reduce((acc, curr)=>{
@@ -3916,16 +3957,16 @@ const FacetEnumList = ({ field, facetName, hooks, valueLabel, isSettings = false
3916
3957
  const remainingValues = tempFilteredData.length + selectedEnumNotInData.length - maxValuesToDisplay;
3917
3958
  const cardStyle = calcCardStyle(remainingValues);
3918
3959
  const numberOfBarsToDisplay = calcNumberOfBarsToDisplay(tempFilteredData.length + selectedEnumNotInData.length);
3960
+ const allData = [
3961
+ ...tempFilteredData,
3962
+ ...selectedEnumNotInData
3963
+ ];
3964
+ // remove any enum in excludeValues
3965
+ const filteredData = allData.filter((x)=>!excludeValues?.includes(x[0].toString()));
3919
3966
  setFacetChartData((prevFacetChartData)=>({
3920
3967
  ...prevFacetChartData,
3921
- filteredData: [
3922
- ...tempFilteredData,
3923
- ...selectedEnumNotInData
3924
- ],
3925
- filteredDataObj: Object.fromEntries([
3926
- ...tempFilteredData,
3927
- ...selectedEnumNotInData
3928
- ]),
3968
+ filteredData: filteredData,
3969
+ filteredDataObj: Object.fromEntries(filteredData),
3929
3970
  remainingValues,
3930
3971
  numberOfBarsToDisplay,
3931
3972
  isSuccess: true,
@@ -3951,8 +3992,9 @@ const FacetEnumList = ({ field, facetName, hooks, valueLabel, isSettings = false
3951
3992
  useDeepCompare.useDeepCompareEffect(()=>{
3952
3993
  if (facetChartData.filteredData && facetChartData.filteredData.length > 0) {
3953
3994
  const obj = [
3954
- ...facetChartData.filteredData
3955
- ].sort(sortType.type === 'value' ? ([, a], [, b])=>sortType.direction === 'dsc' ? b - a : a - b : ([a], [b])=>sortType.direction === 'dsc' ? compareKeysDescending(a, b) : compareKeysAscending(a, b)).slice(0, !isGroupExpanded ? maxValuesToDisplay : undefined);
3995
+ ...facetChartData.filteredData.filter((x)=>!moveValuesToBottom.includes(x[0].toString())).sort(sortType.type === 'value' ? ([, a], [, b])=>sortType.direction === 'dsc' ? b - a : a - b : ([a], [b])=>sortType.direction === 'dsc' ? compareKeysDescending(a, b) : compareKeysAscending(a, b)),
3996
+ ...facetChartData.filteredData.filter((x)=>moveValuesToBottom.includes(x[0].toString()))
3997
+ ].slice(0, !isGroupExpanded ? maxValuesToDisplay : undefined);
3956
3998
  setSortedData(obj);
3957
3999
  if (updateVisibleValues) updateVisibleValues(obj);
3958
4000
  }
@@ -4165,7 +4207,7 @@ const FacetEnumList = ({ field, facetName, hooks, valueLabel, isSettings = false
4165
4207
  });
4166
4208
  };
4167
4209
 
4168
- const EnumFacet = ({ field, hooks, valueLabel, description, facetName, showPercent = true, hideIfEmpty = true, showSearch = true, showFlip = false, showSettings = false, startShowingData = true, dismissCallback = undefined, width = undefined, sharedWithIndices = undefined, header = {
4210
+ const EnumFacet = ({ field, hooks, valueLabel, description, facetName, showPercent = true, hideIfEmpty = true, showSearch = true, showFlip = false, showSettings = false, startShowingData = true, dismissCallback = undefined, width = undefined, sharedWithIndices = undefined, moveValuesToBottom = [], excludeValues = [], header = {
4169
4211
  Panel: FacetHeader,
4170
4212
  Label: FacetText,
4171
4213
  iconStyle: controlsIconStyle
@@ -4216,201 +4258,63 @@ const EnumFacet = ({ field, hooks, valueLabel, description, facetName, showPerce
4216
4258
  isFacetView: isFacetView,
4217
4259
  isSearching: isSearching,
4218
4260
  hideIfEmpty: hideIfEmpty,
4219
- showPercent: showPercent
4261
+ showPercent: showPercent,
4262
+ moveValuesToBottom: moveValuesToBottom,
4263
+ excludeValues: excludeValues
4220
4264
  })
4221
4265
  })
4222
4266
  ]
4223
4267
  });
4224
4268
  };
4225
4269
 
4226
- const instanceOfIncludesExcludes$1 = (op)=>[
4227
- 'in'
4228
- ].includes(op.operator); // TODO: Guppy does not support excludes
4229
- /**
4230
- * Extracts the operands if the operation isIncludes or Excludes. Returns an empty Array
4231
- * if filter is not the correct type.
4232
- * @param operation - filters to extract values from
4233
- */ const extractValues = (operation)=>{
4234
- if (operation && instanceOfIncludesExcludes$1(operation)) {
4235
- return operation.operands;
4236
- }
4237
- return [];
4238
- };
4239
- /**
4240
- * Exact value facet component
4241
- * @param field - field to facet on
4242
- * @param description - description of the facet
4243
- * @param facetName - name of the facet
4244
- * @param dismissCallback - callback function to dismiss the facet
4245
- * @param width - width of the facet
4246
- * @param hooks - hooks to use for the facet
4247
- * @param header - header components
4248
- * @category Facets
4249
- */ const ExactValueFacet = ({ field, description, facetName = undefined, dismissCallback = undefined, width = undefined, hooks, header = {
4270
+ const createBucket = (field, lower, upper)=>({
4271
+ operator: 'and',
4272
+ operands: [
4273
+ {
4274
+ field,
4275
+ operator: '>=',
4276
+ operand: lower
4277
+ },
4278
+ {
4279
+ field,
4280
+ operator: '<=',
4281
+ operand: upper
4282
+ }
4283
+ ]
4284
+ });
4285
+ const RangeFacet = ({ field, hooks, valueLabel, description, facetName, minimum = DEFAULT_MINIMUM, maximum = DEFAULT_MAXIMUM, showSearch = false, showFlip = false, showSettings = false, dismissCallback = undefined, width = undefined, header = {
4250
4286
  Panel: FacetHeader,
4251
4287
  Label: FacetText,
4252
4288
  iconStyle: controlsIconStyle
4253
4289
  } })=>{
4254
- const [textValue, setTextValue] = React.useState(''); // Handle the state of the TextInput
4255
- const clearFilters = hooks.useClearFilter();
4256
- const updateFacetFilters = hooks.useUpdateFacetFilters();
4257
- const facetTitle = facetName ? facetName : core.trimFirstFieldNameToTitle(field, true);
4258
- const facetValue = hooks.useGetFacetFilters(field);
4259
- const textValues = React.useMemo(()=>extractValues(facetValue), [
4260
- facetValue
4261
- ]);
4262
- const isFilterExpanded = hooks.useFilterExpanded && hooks.useFilterExpanded(field);
4263
- const showFilters = isFilterExpanded === undefined || isFilterExpanded;
4264
- const setValues = (values)=>{
4265
- if (values.length > 0) {
4266
- if (facetValue && instanceOfIncludesExcludes$1(facetValue)) {
4267
- // updating facet value
4268
- updateFacetFilters(field, {
4269
- ...facetValue,
4270
- operands: values
4271
- });
4272
- }
4273
- if (facetValue === undefined) {
4274
- // TODO: Assuming Includes by default but this might change to Include|Excludes
4275
- updateFacetFilters(field, {
4276
- operator: 'in',
4277
- field: field,
4278
- operands: values
4279
- });
4280
- }
4281
- } else {
4282
- clearFilters(field);
4283
- }
4284
- };
4285
- const addValue = (s)=>{
4286
- if (s === '') return;
4287
- if (textValues.includes(s)) return;
4288
- setTextValue('');
4289
- setValues([
4290
- ...textValues,
4291
- s
4292
- ]);
4293
- };
4294
- const removeButton = (x)=>{
4295
- return /*#__PURE__*/ jsxRuntime.jsx(core$1.ActionIcon, {
4296
- size: "xs",
4297
- color: "white",
4298
- radius: "xl",
4299
- variant: "transparent",
4300
- onClick: ()=>setValues(textValues.filter((i)=>i !== x)),
4301
- children: /*#__PURE__*/ jsxRuntime.jsx(md.MdClose, {
4302
- size: 10,
4303
- "aria-label": "remove value from filter"
4304
- })
4305
- });
4306
- };
4307
- return /*#__PURE__*/ jsxRuntime.jsxs("div", {
4308
- className: `flex flex-col ${width ? width : 'mx-0'} bg-base-max relative border-base-lighter border-1 rounded-md text-xs transition`,
4309
- children: [
4310
- /*#__PURE__*/ jsxRuntime.jsx(FacetControlsHeader, {
4311
- field: field,
4312
- description: description,
4313
- hooks: hooks,
4314
- facetName: facetName,
4315
- dismissCallback: dismissCallback,
4316
- header: header
4317
- }),
4318
- /*#__PURE__*/ jsxRuntime.jsxs("div", {
4319
- className: showFilters ? 'h-full' : 'h-0 invisible',
4320
- "aria-hidden": !showFilters,
4321
- children: [
4322
- /*#__PURE__*/ jsxRuntime.jsxs("div", {
4323
- className: "flex flex-nowrap items-center p-2",
4324
- children: [
4325
- /*#__PURE__*/ jsxRuntime.jsx(core$1.TextInput, {
4326
- "data-testid": "textbox-add-filter-value",
4327
- size: "sm",
4328
- placeholder: `Enter ${facetTitle}`,
4329
- classNames: {
4330
- root: 'grow',
4331
- input: 'border-r-0 rounded-r-none py-1'
4332
- },
4333
- "aria-label": "enter value to add filter",
4334
- value: textValue,
4335
- onChange: (event)=>setTextValue(event.currentTarget.value)
4336
- }),
4337
- /*#__PURE__*/ jsxRuntime.jsx(core$1.ActionIcon, {
4338
- size: "lg",
4339
- "aria-label": "add string value",
4340
- className: "bg-accent text-accent-contrast border-base-min border-1 rounded-l-none h-[30px]",
4341
- onClick: ()=>{
4342
- if (textValue.length > 0) addValue(textValue.trim());
4343
- },
4344
- children: /*#__PURE__*/ jsxRuntime.jsx(fa.FaPlus, {})
4345
- })
4346
- ]
4347
- }),
4348
- /*#__PURE__*/ jsxRuntime.jsx(core$1.Group, {
4349
- gap: "xs",
4350
- className: "px-2 py-2 max-h-96 overflow-y-auto",
4351
- "data-testid": "values group",
4352
- children: textValues.map((x)=>/*#__PURE__*/ jsxRuntime.jsx(core$1.Badge, {
4353
- size: "sm",
4354
- variant: "filled",
4355
- color: "accent",
4356
- rightSection: removeButton(x),
4357
- children: x
4358
- }, x))
4359
- })
4360
- ]
4361
- })
4362
- ]
4363
- });
4364
- };
4365
-
4366
- const createBucket = (field, lower, upper)=>({
4367
- operator: 'and',
4368
- operands: [
4369
- {
4370
- field,
4371
- operator: '>=',
4372
- operand: lower
4373
- },
4374
- {
4375
- field,
4376
- operator: '<=',
4377
- operand: upper
4378
- }
4379
- ]
4380
- });
4381
- const RangeFacet = ({ field, hooks, valueLabel, description, facetName, minimum = DEFAULT_MINIMUM, maximum = DEFAULT_MAXIMUM, showSearch = false, showFlip = false, showSettings = false, dismissCallback = undefined, width = undefined, header = {
4382
- Panel: FacetHeader,
4383
- Label: FacetText,
4384
- iconStyle: controlsIconStyle
4385
- } })=>{
4386
- const { data, rangeFilters, isSuccess } = hooks.useGetFacetData(field);
4387
- const [minMaxValue, setMinMaxValue] = React.useState({
4388
- from: minimum,
4389
- to: maximum
4390
- });
4391
- const clearRangeFilterFromCohort = hooks.useClearFilter();
4392
- React.useCallback(()=>{
4393
- setMinMaxValue({
4394
- from: minimum,
4395
- to: maximum
4396
- });
4397
- clearRangeFilterFromCohort(field);
4398
- }, [
4399
- clearRangeFilterFromCohort,
4400
- field,
4401
- maximum,
4402
- minimum
4403
- ]);
4404
- const updateRangeFilter = hooks.useUpdateFacetFilters();
4405
- const updateFilters = React.useCallback((from, to)=>{
4406
- updateRangeFilter(field, createBucket(field, from, to));
4407
- setMinMaxValue({
4408
- from: from,
4409
- to: to
4410
- });
4411
- }, [
4412
- field,
4413
- updateRangeFilter
4290
+ const { data, rangeFilters, isSuccess } = hooks.useGetFacetData(field);
4291
+ const [minMaxValue, setMinMaxValue] = React.useState({
4292
+ from: minimum,
4293
+ to: maximum
4294
+ });
4295
+ const clearRangeFilterFromCohort = hooks.useClearFilter();
4296
+ React.useCallback(()=>{
4297
+ setMinMaxValue({
4298
+ from: minimum,
4299
+ to: maximum
4300
+ });
4301
+ clearRangeFilterFromCohort(field);
4302
+ }, [
4303
+ clearRangeFilterFromCohort,
4304
+ field,
4305
+ maximum,
4306
+ minimum
4307
+ ]);
4308
+ const updateRangeFilter = hooks.useUpdateFacetFilters();
4309
+ const updateFilters = React.useCallback((from, to)=>{
4310
+ updateRangeFilter(field, createBucket(field, from, to));
4311
+ setMinMaxValue({
4312
+ from: from,
4313
+ to: to
4314
+ });
4315
+ }, [
4316
+ field,
4317
+ updateRangeFilter
4414
4318
  ]);
4415
4319
  const isFilterExpanded = hooks.useFilterExpanded && hooks.useFilterExpanded(field);
4416
4320
  const showFilters = isFilterExpanded === undefined || isFilterExpanded;
@@ -4491,7 +4395,7 @@ const RangeFacet = ({ field, hooks, valueLabel, description, facetName, minimum
4491
4395
  });
4492
4396
  };
4493
4397
 
4494
- const instanceOfIncludesExcludes = (op)=>[
4398
+ const instanceOfIncludesExcludes$1 = (op)=>[
4495
4399
  'in'
4496
4400
  ].includes(op.operator); // TODO: Guppy does not support excludes
4497
4401
  const isOperandsObject = (obj)=>{
@@ -4540,7 +4444,7 @@ const isFacetEmpty = (op)=>{
4540
4444
  useDeepCompare.useDeepCompareEffect(()=>{
4541
4445
  if (!facetValue || isFacetEmpty(facetValue)) {
4542
4446
  setSelectedValues([]);
4543
- } else if (instanceOfIncludesExcludes(facetValue)) {
4447
+ } else if (instanceOfIncludesExcludes$1(facetValue)) {
4544
4448
  const filters = facetValue.operands.map((x)=>x.toString());
4545
4449
  setSelectedValues(filters);
4546
4450
  }
@@ -4600,6 +4504,556 @@ const isFacetEmpty = (op)=>{
4600
4504
  });
4601
4505
  };
4602
4506
 
4507
+ const instanceOfIncludesExcludes = (op)=>[
4508
+ 'in'
4509
+ ].includes(op.operator); // TODO: Guppy does not support excludes
4510
+ /**
4511
+ * Extracts the operands if the operation isIncludes or Excludes. Returns an empty Array
4512
+ * if filter is not the correct type.
4513
+ * @param operation - filters to extract values from
4514
+ */ const extractValues = (operation)=>{
4515
+ if (operation && instanceOfIncludesExcludes(operation)) {
4516
+ return operation.operands;
4517
+ }
4518
+ return [];
4519
+ };
4520
+ /**
4521
+ * Exact value facet component
4522
+ * @param field - field to facet on
4523
+ * @param description - description of the facet
4524
+ * @param facetName - name of the facet
4525
+ * @param dismissCallback - callback function to dismiss the facet
4526
+ * @param width - width of the facet
4527
+ * @param hooks - hooks to use for the facet
4528
+ * @param header - header components
4529
+ * @category Facets
4530
+ */ const ExactValueFacet = ({ field, description, facetName = undefined, dismissCallback = undefined, width = undefined, hooks, header = {
4531
+ Panel: FacetHeader,
4532
+ Label: FacetText,
4533
+ iconStyle: controlsIconStyle
4534
+ } })=>{
4535
+ const [textValue, setTextValue] = React.useState(''); // Handle the state of the TextInput
4536
+ const clearFilters = hooks.useClearFilter();
4537
+ const updateFacetFilters = hooks.useUpdateFacetFilters();
4538
+ const facetTitle = facetName ? facetName : core.trimFirstFieldNameToTitle(field, true);
4539
+ const facetValue = hooks.useGetFacetFilters(field);
4540
+ const textValues = React.useMemo(()=>extractValues(facetValue), [
4541
+ facetValue
4542
+ ]);
4543
+ const isFilterExpanded = hooks.useFilterExpanded && hooks.useFilterExpanded(field);
4544
+ const showFilters = isFilterExpanded === undefined || isFilterExpanded;
4545
+ const setValues = (values)=>{
4546
+ if (values.length > 0) {
4547
+ if (facetValue && instanceOfIncludesExcludes(facetValue)) {
4548
+ // updating facet value
4549
+ updateFacetFilters(field, {
4550
+ ...facetValue,
4551
+ operands: values
4552
+ });
4553
+ }
4554
+ if (facetValue === undefined) {
4555
+ // TODO: Assuming Includes by default but this might change to Include|Excludes
4556
+ updateFacetFilters(field, {
4557
+ operator: 'in',
4558
+ field: field,
4559
+ operands: values
4560
+ });
4561
+ }
4562
+ } else {
4563
+ clearFilters(field);
4564
+ }
4565
+ };
4566
+ const addValue = (s)=>{
4567
+ if (s === '') return;
4568
+ if (textValues.includes(s)) return;
4569
+ setTextValue('');
4570
+ setValues([
4571
+ ...textValues,
4572
+ s
4573
+ ]);
4574
+ };
4575
+ const removeButton = (x)=>{
4576
+ return /*#__PURE__*/ jsxRuntime.jsx(core$1.ActionIcon, {
4577
+ size: "xs",
4578
+ color: "white",
4579
+ radius: "xl",
4580
+ variant: "transparent",
4581
+ onClick: ()=>setValues(textValues.filter((i)=>i !== x)),
4582
+ children: /*#__PURE__*/ jsxRuntime.jsx(md.MdClose, {
4583
+ size: 10,
4584
+ "aria-label": "remove value from filter"
4585
+ })
4586
+ });
4587
+ };
4588
+ return /*#__PURE__*/ jsxRuntime.jsxs("div", {
4589
+ className: `flex flex-col ${width ? width : 'mx-0'} bg-base-max relative border-base-lighter border-1 rounded-md text-xs transition`,
4590
+ children: [
4591
+ /*#__PURE__*/ jsxRuntime.jsx(FacetControlsHeader, {
4592
+ field: field,
4593
+ description: description,
4594
+ hooks: hooks,
4595
+ facetName: facetName,
4596
+ dismissCallback: dismissCallback,
4597
+ header: header
4598
+ }),
4599
+ /*#__PURE__*/ jsxRuntime.jsxs("div", {
4600
+ className: showFilters ? 'h-full' : 'h-0 invisible',
4601
+ "aria-hidden": !showFilters,
4602
+ children: [
4603
+ /*#__PURE__*/ jsxRuntime.jsxs("div", {
4604
+ className: "flex flex-nowrap items-center p-2",
4605
+ children: [
4606
+ /*#__PURE__*/ jsxRuntime.jsx(core$1.TextInput, {
4607
+ "data-testid": "textbox-add-filter-value",
4608
+ size: "sm",
4609
+ placeholder: `Enter ${facetTitle}`,
4610
+ classNames: {
4611
+ root: 'grow',
4612
+ input: 'border-r-0 rounded-r-none py-1'
4613
+ },
4614
+ "aria-label": "enter value to add filter",
4615
+ value: textValue,
4616
+ onChange: (event)=>setTextValue(event.currentTarget.value)
4617
+ }),
4618
+ /*#__PURE__*/ jsxRuntime.jsx(core$1.ActionIcon, {
4619
+ size: "lg",
4620
+ "aria-label": "add string value",
4621
+ className: "bg-accent text-accent-contrast border-base-min border-1 rounded-l-none h-[30px]",
4622
+ onClick: ()=>{
4623
+ if (textValue.length > 0) addValue(textValue.trim());
4624
+ },
4625
+ children: /*#__PURE__*/ jsxRuntime.jsx(fa.FaPlus, {})
4626
+ })
4627
+ ]
4628
+ }),
4629
+ /*#__PURE__*/ jsxRuntime.jsx(core$1.Group, {
4630
+ gap: "xs",
4631
+ className: "px-2 py-2 max-h-96 overflow-y-auto",
4632
+ "data-testid": "values group",
4633
+ children: textValues.map((x)=>/*#__PURE__*/ jsxRuntime.jsx(core$1.Badge, {
4634
+ size: "sm",
4635
+ variant: "filled",
4636
+ color: "accent",
4637
+ rightSection: removeButton(x),
4638
+ children: x
4639
+ }, x))
4640
+ })
4641
+ ]
4642
+ })
4643
+ ]
4644
+ });
4645
+ };
4646
+
4647
+ const createFacetCard = ({ facetDefinition, valueLabel, hooks: dataFunctions, facetNameFormatter, idPrefix, hideIfEmpty = false, width, showPercent = false, queryOptions })=>{
4648
+ const { field, type, description, label } = facetDefinition;
4649
+ const facetLabel = label ?? facetNameFormatter(facetDefinition.field);
4650
+ const valueTypeLabel = valueLabel === undefined || typeof valueLabel === 'string' ? valueLabel : valueLabel(queryOptions);
4651
+ return /*#__PURE__*/ jsxRuntime.jsx("div", {
4652
+ children: {
4653
+ enum: /*#__PURE__*/ jsxRuntime.jsx(EnumFacet, {
4654
+ valueLabel: valueTypeLabel,
4655
+ field: field,
4656
+ facetName: facetLabel,
4657
+ description: description,
4658
+ hideIfEmpty: hideIfEmpty,
4659
+ width: width,
4660
+ hooks: dataFunctions,
4661
+ showPercent: showPercent,
4662
+ sharedWithIndices: facetDefinition?.sharedWithIndices,
4663
+ moveValuesToBottom: facetDefinition?.moveValuesToBottom ?? [],
4664
+ excludeValues: facetDefinition?.excludeValues ?? []
4665
+ }, `${idPrefix}-enum-${field}`),
4666
+ range: /*#__PURE__*/ jsxRuntime.jsx(RangeFacet, {
4667
+ valueLabel: valueTypeLabel,
4668
+ field: field,
4669
+ facetName: facetLabel,
4670
+ description: description,
4671
+ hideIfEmpty: hideIfEmpty,
4672
+ width: width,
4673
+ hooks: dataFunctions,
4674
+ minimum: facetDefinition.range?.minimum,
4675
+ maximum: facetDefinition.range?.maximum,
4676
+ showSettings: showPercent,
4677
+ sharedWithIndices: facetDefinition?.sharedWithIndices
4678
+ }, `${idPrefix}-range-${field}`),
4679
+ exact: /*#__PURE__*/ jsxRuntime.jsx(ExactValueFacet, {
4680
+ field: field,
4681
+ facetName: facetLabel,
4682
+ description: description,
4683
+ hideIfEmpty: hideIfEmpty,
4684
+ width: width,
4685
+ hooks: dataFunctions,
4686
+ sharedWithIndices: facetDefinition?.sharedWithIndices
4687
+ }, `${idPrefix}-exact-${field}`),
4688
+ multiselect: /*#__PURE__*/ jsxRuntime.jsx(MultiSelectValueFacet, {
4689
+ field: field,
4690
+ facetName: facetLabel,
4691
+ description: description,
4692
+ hideIfEmpty: hideIfEmpty,
4693
+ width: width,
4694
+ hooks: dataFunctions,
4695
+ sharedWithIndices: facetDefinition?.sharedWithIndices
4696
+ }, `${idPrefix}-exact-${field}`)
4697
+ }[type]
4698
+ }, `${idPrefix}-facet-${field}`);
4699
+ };
4700
+
4701
+ const FiltersPanel = ({ fields, dataFunctions, valueLabel })=>{
4702
+ return /*#__PURE__*/ jsxRuntime.jsx("div", {
4703
+ "data-testid": "filters-facets",
4704
+ className: "flex flex-col gap-y-4 w-full",
4705
+ children: fields.map((facetDefinition)=>{
4706
+ if (facetDefinition?.type === undefined) {
4707
+ console.warn('Facet definition missing type', facetDefinition);
4708
+ return null;
4709
+ }
4710
+ if (!(facetDefinition.type in dataFunctions)) return null;
4711
+ return createFacetCard({
4712
+ facetDefinition,
4713
+ valueLabel,
4714
+ hooks: dataFunctions[facetDefinition.type],
4715
+ facetNameFormatter: core.fieldNameToTitle,
4716
+ idPrefix: 'filters-panel',
4717
+ showPercent: false
4718
+ });
4719
+ })
4720
+ });
4721
+ };
4722
+
4723
+ const AccordionPanel = ({ index, filters, tabTitle, facetDefinitions, facetDataHooks, onAccessChange = (value)=>null, accessLevel = core.Accessibility.ALL, showAccessLevel = false })=>{
4724
+ const coreDispatch = core.useCoreDispatch();
4725
+ const sharedFilters = core.useCoreSelector((state)=>core.selectSharedFilters(state));
4726
+ const theme = core$1.useMantineTheme();
4727
+ const shareFilters = core.useCoreSelector((state)=>core.selectShouldShareFilters(state));
4728
+ const allFiltersCollapsed = core.useCoreSelector((state)=>core.selectAllCohortFiltersCollapsed(state, index));
4729
+ const toggleAllFiltersExpanded = (expand)=>{
4730
+ coreDispatch(core.toggleCohortBuilderAllFilters({
4731
+ expand,
4732
+ index
4733
+ }));
4734
+ };
4735
+ const handleSharedFiltersChange = (value)=>{
4736
+ modals.modals.openConfirmModal({
4737
+ title: 'Confirm change of shared filters mode',
4738
+ children: /*#__PURE__*/ jsxRuntime.jsx(core$1.Text, {
4739
+ size: "sm",
4740
+ children: value ? 'Switching to Shared Filters mode will apply all selected filters across all indices.' : 'Switching to Unshared Filters mode will stop syncing filters but will not remove them.'
4741
+ }),
4742
+ labels: {
4743
+ confirm: 'Confirm',
4744
+ cancel: 'Cancel'
4745
+ },
4746
+ onConfirm: ()=>coreDispatch(core.setShouldShareFilters(value))
4747
+ });
4748
+ };
4749
+ return /*#__PURE__*/ jsxRuntime.jsxs(core$1.Stack, {
4750
+ align: "flex-start",
4751
+ children: [
4752
+ /*#__PURE__*/ jsxRuntime.jsxs(core$1.Group, {
4753
+ justify: "space-between",
4754
+ className: "w-full",
4755
+ children: [
4756
+ /*#__PURE__*/ jsxRuntime.jsx(core$1.Text, {
4757
+ size: "xl",
4758
+ fw: 800,
4759
+ children: "Filters"
4760
+ }),
4761
+ /*#__PURE__*/ jsxRuntime.jsx("button", {
4762
+ className: "text-primary text-sm font-normal",
4763
+ onClick: ()=>toggleAllFiltersExpanded(allFiltersCollapsed),
4764
+ children: allFiltersCollapsed ? 'Expand All' : 'Collapse All'
4765
+ })
4766
+ ]
4767
+ }),
4768
+ /*#__PURE__*/ jsxRuntime.jsxs(core$1.Stack, {
4769
+ className: "bg-base-max py-4 px-2 h-full w-full",
4770
+ children: [
4771
+ Object.keys(sharedFilters).length > 0 && /*#__PURE__*/ jsxRuntime.jsxs(core$1.Group, {
4772
+ gap: "xs",
4773
+ justify: "space-between",
4774
+ children: [
4775
+ /*#__PURE__*/ jsxRuntime.jsxs("div", {
4776
+ className: "flex items-center space-x-1",
4777
+ children: [
4778
+ /*#__PURE__*/ jsxRuntime.jsx(react.Icon, {
4779
+ icon: "gen3:share",
4780
+ height: 16,
4781
+ width: 16,
4782
+ color: theme.colors.accent[4]
4783
+ }),
4784
+ /*#__PURE__*/ jsxRuntime.jsx(core$1.Text, {
4785
+ size: "sm",
4786
+ children: "Set the shared filters for all"
4787
+ }),
4788
+ /*#__PURE__*/ jsxRuntime.jsx(react.Icon, {
4789
+ icon: "gen3:info",
4790
+ height: 12,
4791
+ width: 12,
4792
+ color: theme.colors.accent[4]
4793
+ })
4794
+ ]
4795
+ }),
4796
+ /*#__PURE__*/ jsxRuntime.jsx(core$1.Switch, {
4797
+ checked: shareFilters,
4798
+ onChange: (event)=>handleSharedFiltersChange(event.currentTarget.checked)
4799
+ })
4800
+ ]
4801
+ }),
4802
+ /*#__PURE__*/ jsxRuntime.jsx(core$1.Accordion, {
4803
+ chevronPosition: "left",
4804
+ multiple: true,
4805
+ defaultValue: [
4806
+ filters?.tabs[0].title ?? 'Filters'
4807
+ ],
4808
+ children: filters.tabs.map((tab)=>{
4809
+ return /*#__PURE__*/ jsxRuntime.jsxs(core$1.Accordion.Item, {
4810
+ value: tab.title,
4811
+ children: [
4812
+ /*#__PURE__*/ jsxRuntime.jsx(core$1.Accordion.Control, {
4813
+ children: tab.title
4814
+ }),
4815
+ /*#__PURE__*/ jsxRuntime.jsx(core$1.Accordion.Panel, {
4816
+ classNames: {
4817
+ panel: 'p-0 m-0'
4818
+ },
4819
+ children: Object.keys(facetDefinitions).length > 0 ? /*#__PURE__*/ jsxRuntime.jsx(FiltersPanel, {
4820
+ fields: tab.fields.reduce((acc, field)=>{
4821
+ return [
4822
+ ...acc,
4823
+ facetDefinitions[field]
4824
+ ];
4825
+ }, []),
4826
+ dataFunctions: facetDataHooks,
4827
+ valueLabel: tabTitle
4828
+ }) : null
4829
+ })
4830
+ ]
4831
+ }, `${tab.title}`);
4832
+ })
4833
+ })
4834
+ ]
4835
+ })
4836
+ ]
4837
+ });
4838
+ };
4839
+
4840
+ const AccessData = [
4841
+ {
4842
+ value: core.Accessibility.ALL,
4843
+ label: 'All'
4844
+ },
4845
+ {
4846
+ value: core.Accessibility.ACCESSIBLE,
4847
+ label: 'Accessible'
4848
+ },
4849
+ {
4850
+ value: core.Accessibility.UNACCESSIBLE,
4851
+ label: 'Not Accessible'
4852
+ }
4853
+ ];
4854
+ const AccessLevelControl = ({ onChange, accessLevel })=>{
4855
+ const theme = core$1.useMantineTheme();
4856
+ return /*#__PURE__*/ jsxRuntime.jsx(core$1.SegmentedControl, {
4857
+ color: theme.colors.accent[5],
4858
+ data: AccessData,
4859
+ value: accessLevel,
4860
+ onChange: (val)=>{
4861
+ const accessibilityValue = AccessData.find((item)=>item.value === val)?.value || core.Accessibility.ALL;
4862
+ onChange(accessibilityValue);
4863
+ }
4864
+ });
4865
+ };
4866
+
4867
+ const DropdownPanel = ({ index, filters, tabTitle, facetDefinitions, facetDataHooks, onAccessChange = (value)=>null, accessLevel = core.Accessibility.ALL, showAccessLevel = false })=>{
4868
+ const [value, setValue] = React.useState('0');
4869
+ const allFiltersCollapsed = core.useCoreSelector((state)=>core.selectAllCohortFiltersCollapsed(state, index));
4870
+ const sharedFilters = core.useCoreSelector((state)=>core.selectSharedFilters(state));
4871
+ const shareFilters = core.useCoreSelector((state)=>core.selectShouldShareFilters(state));
4872
+ const theme = core$1.useMantineTheme();
4873
+ const coreDispatch = core.useCoreDispatch();
4874
+ const toggleAllFiltersExpanded = (expand)=>{
4875
+ coreDispatch(core.toggleCohortBuilderAllFilters({
4876
+ expand,
4877
+ index
4878
+ }));
4879
+ };
4880
+ const items = useDeepCompare.useDeepCompareMemo(()=>filters.tabs.map((tab, idx)=>{
4881
+ return {
4882
+ label: tab.title,
4883
+ value: idx.toString()
4884
+ };
4885
+ }), [
4886
+ filters.tabs
4887
+ ]);
4888
+ const fields = filters.tabs[Number(value)].fields.reduce((acc, field)=>{
4889
+ return [
4890
+ ...acc,
4891
+ facetDefinitions[field]
4892
+ ];
4893
+ }, []);
4894
+ const handleSharedFiltersChange = (value)=>{
4895
+ modals.modals.openConfirmModal({
4896
+ title: 'Confirm change of shared filters mode',
4897
+ children: /*#__PURE__*/ jsxRuntime.jsx(core$1.Text, {
4898
+ size: "sm",
4899
+ children: value ? 'Switching to Shared Filters mode will apply all selected filters across all indices.' : 'Switching to Unshared Filters mode will stop syncing filters but will not remove them.'
4900
+ }),
4901
+ labels: {
4902
+ confirm: 'Confirm',
4903
+ cancel: 'Cancel'
4904
+ },
4905
+ onConfirm: ()=>coreDispatch(core.setShouldShareFilters(value))
4906
+ });
4907
+ };
4908
+ return /*#__PURE__*/ jsxRuntime.jsxs(core$1.Stack, {
4909
+ align: "flex-start",
4910
+ children: [
4911
+ /*#__PURE__*/ jsxRuntime.jsxs(core$1.Group, {
4912
+ justify: "space-between",
4913
+ className: "w-full",
4914
+ children: [
4915
+ /*#__PURE__*/ jsxRuntime.jsx(core$1.Text, {
4916
+ size: "xl",
4917
+ fw: 800,
4918
+ children: "Filters"
4919
+ }),
4920
+ /*#__PURE__*/ jsxRuntime.jsx("button", {
4921
+ className: "text-primary text-sm font-normal",
4922
+ onClick: ()=>toggleAllFiltersExpanded(allFiltersCollapsed),
4923
+ children: allFiltersCollapsed ? 'Expand All' : 'Collapse All'
4924
+ })
4925
+ ]
4926
+ }),
4927
+ showAccessLevel ? /*#__PURE__*/ jsxRuntime.jsx(AccessLevelControl, {
4928
+ onChange: onAccessChange,
4929
+ accessLevel: accessLevel
4930
+ }) : null,
4931
+ /*#__PURE__*/ jsxRuntime.jsxs(core$1.Stack, {
4932
+ className: "bg-base-max py-4 px-2 h-full w-full",
4933
+ children: [
4934
+ Object.keys(sharedFilters).length > 0 && /*#__PURE__*/ jsxRuntime.jsxs(core$1.Group, {
4935
+ gap: "xs",
4936
+ justify: "space-between",
4937
+ children: [
4938
+ /*#__PURE__*/ jsxRuntime.jsxs("div", {
4939
+ className: "flex items-center space-x-1",
4940
+ children: [
4941
+ /*#__PURE__*/ jsxRuntime.jsx(react.Icon, {
4942
+ icon: "gen3:share",
4943
+ height: 16,
4944
+ width: 16,
4945
+ color: theme.colors.accent[4]
4946
+ }),
4947
+ /*#__PURE__*/ jsxRuntime.jsx(core$1.Text, {
4948
+ size: "sm",
4949
+ children: "Set the shared filters for all"
4950
+ }),
4951
+ /*#__PURE__*/ jsxRuntime.jsx(core$1.Tooltip, {
4952
+ label: "If enabled any filter set on this tab will be applied to every tab where occurs.",
4953
+ position: "top",
4954
+ withArrow: true,
4955
+ children: /*#__PURE__*/ jsxRuntime.jsx(react.Icon, {
4956
+ icon: "gen3:info",
4957
+ height: 12,
4958
+ width: 12,
4959
+ color: theme.colors.accent[4]
4960
+ })
4961
+ })
4962
+ ]
4963
+ }),
4964
+ /*#__PURE__*/ jsxRuntime.jsx(core$1.Switch, {
4965
+ checked: shareFilters,
4966
+ onChange: (event)=>handleSharedFiltersChange(event.currentTarget.checked)
4967
+ })
4968
+ ]
4969
+ }),
4970
+ filters.tabs.length > 1 && /*#__PURE__*/ jsxRuntime.jsx(core$1.Select, {
4971
+ classNames: {
4972
+ options: 'border-1 border-base-dark',
4973
+ option: 'hover:bg-primary-lightest'
4974
+ },
4975
+ withCheckIcon: false,
4976
+ data: items,
4977
+ value: value === null ? '0' : value,
4978
+ onChange: setValue
4979
+ }),
4980
+ Object.keys(facetDefinitions).length > 0 ? /*#__PURE__*/ jsxRuntime.jsx(FiltersPanel, {
4981
+ fields: fields,
4982
+ dataFunctions: facetDataHooks,
4983
+ valueLabel: tabTitle
4984
+ }) : null
4985
+ ]
4986
+ })
4987
+ ]
4988
+ });
4989
+ };
4990
+
4991
+ const VerticalTabbedPanel = ({ index, filters, tabTitle, facetDefinitions, facetDataHooks, onAccessChange = (value)=>null, accessLevel = core.Accessibility.ALL, showAccessLevel = false })=>{
4992
+ return /*#__PURE__*/ jsxRuntime.jsx("div", {
4993
+ children: /*#__PURE__*/ jsxRuntime.jsxs(core$1.Tabs, {
4994
+ variant: "pills",
4995
+ orientation: "vertical",
4996
+ keepMounted: false,
4997
+ defaultValue: filters?.tabs[0].title ?? 'Filters',
4998
+ children: [
4999
+ /*#__PURE__*/ jsxRuntime.jsx(core$1.Tabs.List, {
5000
+ children: filters.tabs.map((tab)=>{
5001
+ return /*#__PURE__*/ jsxRuntime.jsx(core$1.Tabs.Tab, {
5002
+ value: tab.title,
5003
+ children: tab.title
5004
+ }, `${tab.title}-tab`);
5005
+ })
5006
+ }),
5007
+ filters.tabs.map((tab)=>{
5008
+ return /*#__PURE__*/ jsxRuntime.jsx(core$1.Tabs.Panel, {
5009
+ value: tab.title,
5010
+ className: "w-1/4",
5011
+ children: Object.keys(facetDefinitions).length > 0 ? /*#__PURE__*/ jsxRuntime.jsx(FiltersPanel, {
5012
+ fields: tab.fields.reduce((acc, field)=>{
5013
+ return [
5014
+ ...acc,
5015
+ facetDefinitions[field]
5016
+ ];
5017
+ }, []),
5018
+ dataFunctions: facetDataHooks,
5019
+ valueLabel: tabTitle
5020
+ }) : null
5021
+ }, `filter-${tab.title}-tabPanel`);
5022
+ })
5023
+ ]
5024
+ })
5025
+ });
5026
+ };
5027
+ const SinglePanel = ({ filters, tabTitle, facetDefinitions, facetDataHooks })=>{
5028
+ return /*#__PURE__*/ jsxRuntime.jsx("div", {
5029
+ children: Object.keys(facetDefinitions).length > 0 ? /*#__PURE__*/ jsxRuntime.jsx(FiltersPanel, {
5030
+ fields: filters.tabs[0].fields.reduce((acc, field)=>{
5031
+ return [
5032
+ ...acc,
5033
+ facetDefinitions[field]
5034
+ ];
5035
+ }, []),
5036
+ dataFunctions: facetDataHooks,
5037
+ valueLabel: tabTitle
5038
+ }) : null
5039
+ });
5040
+ };
5041
+ const TabbedPanel = ({ index, filters, tabTitle, facetDefinitions, facetDataHooks })=>{
5042
+ return filters.tabs.length > 1 ? /*#__PURE__*/ jsxRuntime.jsx(VerticalTabbedPanel, {
5043
+ index: index,
5044
+ filters: filters,
5045
+ tabTitle: tabTitle,
5046
+ facetDefinitions: facetDefinitions,
5047
+ facetDataHooks: facetDataHooks
5048
+ }) : /*#__PURE__*/ jsxRuntime.jsx(SinglePanel, {
5049
+ index: index,
5050
+ filters: filters,
5051
+ tabTitle: tabTitle,
5052
+ facetDefinitions: facetDefinitions,
5053
+ facetDataHooks: facetDataHooks
5054
+ });
5055
+ };
5056
+
4603
5057
  /**
4604
5058
  * Scrolls to hash in url when component mounts and removes hash from url when component unmounts
4605
5059
  * @param valid_hashes - what hashes in url should trigger scroll
@@ -4621,58 +5075,6 @@ const isFacetEmpty = (op)=>{
4621
5075
  }, []);
4622
5076
  };
4623
5077
 
4624
- const createFacetCard = ({ facetDefinition, valueLabel, hooks: dataFunctions, facetNameFormatter, idPrefix, hideIfEmpty = false, width, showPercent = false, queryOptions })=>{
4625
- const { field, type, description, label } = facetDefinition;
4626
- const facetLabel = label ?? facetNameFormatter(facetDefinition.field);
4627
- const valueTypeLabel = valueLabel === undefined || typeof valueLabel === 'string' ? valueLabel : valueLabel(queryOptions);
4628
- return /*#__PURE__*/ jsxRuntime.jsx("div", {
4629
- children: {
4630
- enum: /*#__PURE__*/ jsxRuntime.jsx(EnumFacet, {
4631
- valueLabel: valueTypeLabel,
4632
- field: field,
4633
- facetName: facetLabel,
4634
- description: description,
4635
- hideIfEmpty: hideIfEmpty,
4636
- width: width,
4637
- hooks: dataFunctions,
4638
- showPercent: showPercent,
4639
- sharedWithIndices: facetDefinition?.sharedWithIndices
4640
- }, `${idPrefix}-enum-${field}`),
4641
- range: /*#__PURE__*/ jsxRuntime.jsx(RangeFacet, {
4642
- valueLabel: valueTypeLabel,
4643
- field: field,
4644
- facetName: facetLabel,
4645
- description: description,
4646
- hideIfEmpty: hideIfEmpty,
4647
- width: width,
4648
- hooks: dataFunctions,
4649
- minimum: facetDefinition.range?.minimum,
4650
- maximum: facetDefinition.range?.maximum,
4651
- showSettings: showPercent,
4652
- sharedWithIndices: facetDefinition?.sharedWithIndices
4653
- }, `${idPrefix}-range-${field}`),
4654
- exact: /*#__PURE__*/ jsxRuntime.jsx(ExactValueFacet, {
4655
- field: field,
4656
- facetName: facetLabel,
4657
- description: description,
4658
- hideIfEmpty: hideIfEmpty,
4659
- width: width,
4660
- hooks: dataFunctions,
4661
- sharedWithIndices: facetDefinition?.sharedWithIndices
4662
- }, `${idPrefix}-exact-${field}`),
4663
- multiselect: /*#__PURE__*/ jsxRuntime.jsx(MultiSelectValueFacet, {
4664
- field: field,
4665
- facetName: facetLabel,
4666
- description: description,
4667
- hideIfEmpty: hideIfEmpty,
4668
- width: width,
4669
- hooks: dataFunctions,
4670
- sharedWithIndices: facetDefinition?.sharedWithIndices
4671
- }, `${idPrefix}-exact-${field}`)
4672
- }[type]
4673
- }, `${idPrefix}-facet-${field}`);
4674
- };
4675
-
4676
5078
  const createFacetCards = ({ facets, hooks, facetNameFormatter, idPrefix, valueLabel, dismissCallback, hideIfEmpty, Chart, showPercent })=>{
4677
5079
  return facets.map((facetDefinition)=>{
4678
5080
  return createFacetCard({
@@ -7167,6 +7569,20 @@ const TableIcons = {
7167
7569
  })
7168
7570
  };
7169
7571
 
7572
+ const CompareFn = (fieldValue, cmpOp, value)=>{
7573
+ switch(cmpOp){
7574
+ case 'alwaysTrue':
7575
+ return true;
7576
+ case 'arrayNotEmpty':
7577
+ return Array.isArray(fieldValue) && fieldValue.length > 0;
7578
+ }
7579
+ };
7580
+ const isSelectable = (row, config)=>{
7581
+ if (!config) return false;
7582
+ if (!Object.hasOwn(row.original, config.field)) return false;
7583
+ const fieldValue = row.original[config.field];
7584
+ return CompareFn(fieldValue, config.comparer, config.value);
7585
+ };
7170
7586
  const extractCellValue = (func)=>({ cell, row })=>func({
7171
7587
  value: cell.getValue(),
7172
7588
  cell,
@@ -7199,6 +7615,13 @@ const DiscoveryTable = ({ data, hits, dataRequestStatus, setSorting, setPaginati
7199
7615
  }, [
7200
7616
  config.studyColumns
7201
7617
  ]);
7618
+ const checkIfRowIsSelectable = (row)=>{
7619
+ if (config.tableConfig?.selectableRows) return true;
7620
+ if (config.tableConfig?.selectableRowConfiguration) {
7621
+ return isSelectable(row, config.tableConfig.selectableRowConfiguration);
7622
+ }
7623
+ return false;
7624
+ };
7202
7625
  const table = mantineReactTable.useMantineReactTable({
7203
7626
  columns: cols,
7204
7627
  data: data ?? [],
@@ -7209,7 +7632,7 @@ const DiscoveryTable = ({ data, hits, dataRequestStatus, setSorting, setPaginati
7209
7632
  onPaginationChange: setPagination,
7210
7633
  onSortingChange: setSorting
7211
7634
  } : {},
7212
- enableRowSelection: config.tableConfig?.selectableRows ?? false,
7635
+ enableRowSelection: checkIfRowIsSelectable,
7213
7636
  rowCount: hits,
7214
7637
  icons: TableIcons,
7215
7638
  enableTopToolbar: false,
@@ -8437,6 +8860,7 @@ const useSearchMetadata = ({ discoveryConfig, searchTerms, mdsData, isSuccess })
8437
8860
  uidField
8438
8861
  ],
8439
8862
  idField: uidField,
8863
+ tokenize: (string, _fieldName)=>string.split(' '),
8440
8864
  extractField: extractValue,
8441
8865
  // processTerm: (term) => suffixes(term, 3),
8442
8866
  searchOptions: {
@@ -9340,7 +9764,8 @@ registerDefaultDiscoveryDataLoaders();
9340
9764
  }) : null,
9341
9765
  discoveryConfig.features?.chartsSection?.enabled && /*#__PURE__*/ jsxRuntime.jsx(CollapsableCharts, {
9342
9766
  config: discoveryConfig.features?.chartsSection,
9343
- data: chartData
9767
+ data: chartData,
9768
+ isSuccess: dataRequestStatus.isSuccess
9344
9769
  }),
9345
9770
  /*#__PURE__*/ jsxRuntime.jsxs("div", {
9346
9771
  className: "flex items-center p-2 mb-4 bg-base-max rounded-lg",
@@ -9770,6 +10195,23 @@ const RenderParagraphsCell = ({ value })=>{
9770
10195
  }, i))
9771
10196
  });
9772
10197
  };
10198
+ const RenderIfArrayHasData = ({ value })=>{
10199
+ const content = value;
10200
+ if (lodash.isArray(content) && content.length > 0) {
10201
+ return /*#__PURE__*/ jsxRuntime.jsx(react.Icon, {
10202
+ icon: "gen3:checked-filled",
10203
+ height: 22,
10204
+ width: 22,
10205
+ className: "text-utility-success"
10206
+ });
10207
+ }
10208
+ return /*#__PURE__*/ jsxRuntime.jsx(react.Icon, {
10209
+ icon: "gen3:cancel-filled",
10210
+ height: 22,
10211
+ width: 22,
10212
+ className: "text-utility-error"
10213
+ });
10214
+ };
9773
10215
  // TODO Fix below
9774
10216
  // eslint-disable-next-line react/prop-types
9775
10217
  const DiscoveryRenderTagsCell = ({ value })=>{
@@ -9800,6 +10242,7 @@ const DiscoveryRenderTagsCell = ({ value })=>{
9800
10242
  const Gen3DiscoveryStandardCellRenderers = {
9801
10243
  array: {
9802
10244
  NegativePositive: RenderArrayCellNegativePositive$1,
10245
+ HasData: RenderIfArrayHasData,
9803
10246
  default: RenderArrayCell$1
9804
10247
  },
9805
10248
  string: {
@@ -12164,237 +12607,64 @@ const DownloadsPanel = ({ dropdowns, buttons, loginForDownload, index, totalCoun
12164
12607
  title: `${button.title} (Login Required)`,
12165
12608
  enabled: false
12166
12609
  }))
12167
- }
12168
- };
12169
- }, {});
12170
- }
12171
- return dropdownsToRender;
12172
- }, [
12173
- dropdowns,
12174
- loginRequired,
12175
- isUserLoggedIn
12176
- ]);
12177
- return dropdowns || buttons ? /*#__PURE__*/ jsxRuntime.jsxs("div", {
12178
- className: "flex space-x-1",
12179
- children: [
12180
- Object.values(dropdownsToRender).map((dropdown)=>{
12181
- return createDownloadMenuButton(dropdown, {
12182
- type: index,
12183
- totalCount,
12184
- fields,
12185
- filter,
12186
- accessibility: accessibility ?? core.Accessibility.ALL
12187
- });
12188
- }),
12189
- buttons.map((button)=>{
12190
- let disabled = false;
12191
- let actionFunction = NullButtonAction;
12192
- let actionArgs = {};
12193
- const buttonAction = button.action ?? button.type;
12194
- if (buttonAction) {
12195
- const actionItem = findButtonAction(buttonAction);
12196
- if (actionItem) {
12197
- const funcArgs = actionItem.args ?? {};
12198
- const func = actionItem.action;
12199
- actionFunction = func;
12200
- actionArgs = funcArgs ?? {};
12201
- }
12202
- }
12203
- if (loginRequired && !isUserLoggedIn) {
12204
- disabled = true;
12205
- }
12206
- return /*#__PURE__*/ jsxRuntime.jsx(CohortActionButton, {
12207
- activeText: 'Downloading...',
12208
- inactiveText: button.title,
12209
- tooltipText: button.tooltipText,
12210
- disabled: disabled || !button.enabled,
12211
- actionFunction: actionFunction,
12212
- actionArgs: {
12213
- ...actionArgs,
12214
- ...button.actionArgs ?? {},
12215
- type: index,
12216
- totalCount,
12217
- fields,
12218
- filter,
12219
- accessibility: accessibility ?? core.Accessibility.ALL
12220
- }
12221
- }, button.title);
12222
- })
12223
- ]
12224
- }) : /*#__PURE__*/ jsxRuntime.jsx(React.Fragment, {});
12225
- };
12226
-
12227
- const FiltersPanel = ({ fields, dataFunctions, valueLabel })=>{
12228
- return /*#__PURE__*/ jsxRuntime.jsx("div", {
12229
- "data-testid": "filters-facets",
12230
- className: "flex flex-col gap-y-4 w-full",
12231
- children: fields.map((facetDefinition)=>{
12232
- if (facetDefinition?.type === undefined) {
12233
- console.warn('Facet definition missing type', facetDefinition);
12234
- return null;
12235
- }
12236
- if (!(facetDefinition.type in dataFunctions)) return null;
12237
- return createFacetCard({
12238
- facetDefinition,
12239
- valueLabel,
12240
- hooks: dataFunctions[facetDefinition.type],
12241
- facetNameFormatter: core.fieldNameToTitle,
12242
- idPrefix: 'filters-panel',
12243
- showPercent: false
12244
- });
12245
- })
12246
- });
12247
- };
12248
-
12249
- const AccessData = [
12250
- {
12251
- value: core.Accessibility.ALL,
12252
- label: 'All'
12253
- },
12254
- {
12255
- value: core.Accessibility.ACCESSIBLE,
12256
- label: 'Accessible'
12257
- },
12258
- {
12259
- value: core.Accessibility.UNACCESSIBLE,
12260
- label: 'Not Accessible'
12261
- }
12262
- ];
12263
- const AccessLevelControl = ({ onChange, accessLevel })=>{
12264
- const theme = core$1.useMantineTheme();
12265
- return /*#__PURE__*/ jsxRuntime.jsx(core$1.SegmentedControl, {
12266
- color: theme.colors.accent[5],
12267
- data: AccessData,
12268
- value: accessLevel,
12269
- onChange: (val)=>{
12270
- const accessibilityValue = AccessData.find((item)=>item.value === val)?.value || core.Accessibility.ALL;
12271
- onChange(accessibilityValue);
12272
- }
12273
- });
12274
- };
12275
-
12276
- const DropdownPanel = ({ index, filters, tabTitle, facetDefinitions, facetDataHooks, onAccessChange = (value)=>null, accessLevel = core.Accessibility.ALL, showAccessLevel = false })=>{
12277
- const [value, setValue] = React.useState('0');
12278
- const allFiltersCollapsed = core.useCoreSelector((state)=>core.selectAllCohortFiltersCollapsed(state, index));
12279
- const sharedFilters = core.useCoreSelector((state)=>core.selectSharedFilters(state));
12280
- const shareFilters = core.useCoreSelector((state)=>core.selectShouldShareFilters(state));
12281
- const theme = core$1.useMantineTheme();
12282
- const coreDispatch = core.useCoreDispatch();
12283
- const toggleAllFiltersExpanded = (expand)=>{
12284
- coreDispatch(core.toggleCohortBuilderAllFilters({
12285
- expand,
12286
- index
12287
- }));
12288
- };
12289
- const items = useDeepCompare.useDeepCompareMemo(()=>filters.tabs.map((tab, idx)=>{
12290
- return {
12291
- label: tab.title,
12292
- value: idx.toString()
12293
- };
12294
- }), [
12295
- filters.tabs
12296
- ]);
12297
- const fields = filters.tabs[Number(value)].fields.reduce((acc, field)=>{
12298
- return [
12299
- ...acc,
12300
- facetDefinitions[field]
12301
- ];
12302
- }, []);
12303
- const handleSharedFiltersChange = (value)=>{
12304
- modals.modals.openConfirmModal({
12305
- title: 'Confirm change of shared filters mode',
12306
- children: /*#__PURE__*/ jsxRuntime.jsx(core$1.Text, {
12307
- size: "sm",
12308
- children: value ? 'Switching to Shared Filters mode will apply all selected filters across all indices.' : 'Switching to Unshared Filters mode will stop syncing filters but will not remove them.'
12309
- }),
12310
- labels: {
12311
- confirm: 'Confirm',
12312
- cancel: 'Cancel'
12313
- },
12314
- onConfirm: ()=>coreDispatch(core.setShouldShareFilters(value))
12315
- });
12316
- };
12317
- return /*#__PURE__*/ jsxRuntime.jsxs(core$1.Stack, {
12318
- align: "flex-start",
12610
+ }
12611
+ };
12612
+ }, {});
12613
+ }
12614
+ return dropdownsToRender;
12615
+ }, [
12616
+ dropdowns,
12617
+ loginRequired,
12618
+ isUserLoggedIn
12619
+ ]);
12620
+ return dropdowns || buttons ? /*#__PURE__*/ jsxRuntime.jsxs("div", {
12621
+ className: "flex space-x-1",
12319
12622
  children: [
12320
- /*#__PURE__*/ jsxRuntime.jsxs(core$1.Group, {
12321
- justify: "space-between",
12322
- className: "w-full",
12323
- children: [
12324
- /*#__PURE__*/ jsxRuntime.jsx(core$1.Text, {
12325
- size: "xl",
12326
- fw: 800,
12327
- children: "Filters"
12328
- }),
12329
- /*#__PURE__*/ jsxRuntime.jsx("button", {
12330
- className: "text-primary text-sm font-normal",
12331
- onClick: ()=>toggleAllFiltersExpanded(allFiltersCollapsed),
12332
- children: allFiltersCollapsed ? 'Expand All' : 'Collapse All'
12333
- })
12334
- ]
12623
+ Object.values(dropdownsToRender).map((dropdown)=>{
12624
+ return createDownloadMenuButton(dropdown, {
12625
+ type: index,
12626
+ totalCount,
12627
+ fields,
12628
+ filter,
12629
+ accessibility: accessibility ?? core.Accessibility.ALL
12630
+ });
12335
12631
  }),
12336
- showAccessLevel ? /*#__PURE__*/ jsxRuntime.jsx(AccessLevelControl, {
12337
- onChange: onAccessChange,
12338
- accessLevel: accessLevel
12339
- }) : null,
12340
- /*#__PURE__*/ jsxRuntime.jsxs(core$1.Stack, {
12341
- className: "bg-base-max py-4 px-2 h-full w-full",
12342
- children: [
12343
- Object.keys(sharedFilters).length > 0 && /*#__PURE__*/ jsxRuntime.jsxs(core$1.Group, {
12344
- gap: "xs",
12345
- justify: "space-between",
12346
- children: [
12347
- /*#__PURE__*/ jsxRuntime.jsxs("div", {
12348
- className: "flex items-center space-x-1",
12349
- children: [
12350
- /*#__PURE__*/ jsxRuntime.jsx(react.Icon, {
12351
- icon: "gen3:share",
12352
- height: 16,
12353
- width: 16,
12354
- color: theme.colors.accent[4]
12355
- }),
12356
- /*#__PURE__*/ jsxRuntime.jsx(core$1.Text, {
12357
- size: "sm",
12358
- children: "Set the shared filters for all"
12359
- }),
12360
- /*#__PURE__*/ jsxRuntime.jsx(core$1.Tooltip, {
12361
- label: "If enabled any filter set on this tab will be applied to every tab where occurs.",
12362
- position: "top",
12363
- withArrow: true,
12364
- children: /*#__PURE__*/ jsxRuntime.jsx(react.Icon, {
12365
- icon: "gen3:info",
12366
- height: 12,
12367
- width: 12,
12368
- color: theme.colors.accent[4]
12369
- })
12370
- })
12371
- ]
12372
- }),
12373
- /*#__PURE__*/ jsxRuntime.jsx(core$1.Switch, {
12374
- checked: shareFilters,
12375
- onChange: (event)=>handleSharedFiltersChange(event.currentTarget.checked)
12376
- })
12377
- ]
12378
- }),
12379
- filters.tabs.length > 1 && /*#__PURE__*/ jsxRuntime.jsx(core$1.Select, {
12380
- classNames: {
12381
- options: 'border-1 border-base-dark',
12382
- option: 'hover:bg-primary-lightest'
12383
- },
12384
- withCheckIcon: false,
12385
- data: items,
12386
- value: value === null ? '0' : value,
12387
- onChange: setValue
12388
- }),
12389
- Object.keys(facetDefinitions).length > 0 ? /*#__PURE__*/ jsxRuntime.jsx(FiltersPanel, {
12390
- fields: fields,
12391
- dataFunctions: facetDataHooks,
12392
- valueLabel: tabTitle
12393
- }) : null
12394
- ]
12632
+ buttons.map((button)=>{
12633
+ let disabled = false;
12634
+ let actionFunction = NullButtonAction;
12635
+ let actionArgs = {};
12636
+ const buttonAction = button.action ?? button.type;
12637
+ if (buttonAction) {
12638
+ const actionItem = findButtonAction(buttonAction);
12639
+ if (actionItem) {
12640
+ const funcArgs = actionItem.args ?? {};
12641
+ const func = actionItem.action;
12642
+ actionFunction = func;
12643
+ actionArgs = funcArgs ?? {};
12644
+ }
12645
+ }
12646
+ if (loginRequired && !isUserLoggedIn) {
12647
+ disabled = true;
12648
+ }
12649
+ return /*#__PURE__*/ jsxRuntime.jsx(CohortActionButton, {
12650
+ activeText: 'Downloading...',
12651
+ inactiveText: button.title,
12652
+ tooltipText: button.tooltipText,
12653
+ disabled: disabled || !button.enabled,
12654
+ actionFunction: actionFunction,
12655
+ actionArgs: {
12656
+ ...actionArgs,
12657
+ ...button.actionArgs ?? {},
12658
+ type: index,
12659
+ totalCount,
12660
+ fields,
12661
+ filter,
12662
+ accessibility: accessibility ?? core.Accessibility.ALL
12663
+ }
12664
+ }, button.title);
12395
12665
  })
12396
12666
  ]
12397
- });
12667
+ }) : /*#__PURE__*/ jsxRuntime.jsx(React.Fragment, {});
12398
12668
  };
12399
12669
 
12400
12670
  const EmptyData = {};
@@ -12422,10 +12692,22 @@ const EmptyData = {};
12422
12692
  const isXl = hooks.useMediaQuery('(min-width: 1600px)');
12423
12693
  const [accessLevel, setAccessLevel] = React.useState(core.Accessibility.ALL);
12424
12694
  const sharedFiltersMap = core.useCoreSelector((state)=>core.selectSharedFilters(state));
12425
- let numCols = 3;
12426
- if (isSm) numCols = 1;
12427
- if (isMd) numCols = 2;
12428
- if (isXl) numCols = 4;
12695
+ const defaultDropdowns = React.useMemo(()=>dropdowns ?? {}, [
12696
+ dropdowns
12697
+ ]);
12698
+ const defaultButtons = React.useMemo(()=>buttons ?? [], [
12699
+ buttons
12700
+ ]);
12701
+ const numCols = React.useMemo(()=>{
12702
+ if (isSm) return 1;
12703
+ if (isMd) return 2;
12704
+ if (isXl) return 4;
12705
+ return 3;
12706
+ }, [
12707
+ isSm,
12708
+ isMd,
12709
+ isXl
12710
+ ]);
12429
12711
  const index = guppyConfig.dataType;
12430
12712
  const fields = React.useMemo(()=>getAllFieldsFromFilterConfigs(filters?.tabs ?? []), [
12431
12713
  filters?.tabs
@@ -12439,14 +12721,20 @@ const EmptyData = {};
12439
12721
  filters: cohortFilters,
12440
12722
  accessibility: accessLevel
12441
12723
  });
12442
- const { data: chartData, isSuccess: isChartSuccess, isFetching: isChartFetching, isError: isChartError } = core.useGetAggsNoFilterSelfQuery({
12443
- type: index,
12444
- fields: [
12724
+ const chartKeys = useDeepCompare.useDeepCompareMemo(()=>[
12445
12725
  ...Object.keys(chartsSection?.charts ?? {}),
12446
12726
  ...Object.keys(charts)
12447
- ],
12727
+ ], [
12728
+ chartsSection?.charts,
12729
+ charts
12730
+ ]);
12731
+ const { data: chartData, isSuccess: isChartSuccess, isFetching: isChartFetching, isError: isChartError } = core.useGetAggsNoFilterSelfQuery({
12732
+ type: index,
12733
+ fields: chartKeys,
12448
12734
  filters: cohortFilters,
12449
12735
  accessibility: accessLevel
12736
+ }, {
12737
+ skip: chartKeys.length === 0
12450
12738
  });
12451
12739
  const getEnumFacetData = useDeepCompare.useDeepCompareCallback((field)=>{
12452
12740
  let filters = undefined;
@@ -12469,7 +12757,7 @@ const EmptyData = {};
12469
12757
  isSuccess: isSuccess
12470
12758
  };
12471
12759
  }, [
12472
- cohortFilters,
12760
+ cohortFilters.root,
12473
12761
  data,
12474
12762
  isSuccess
12475
12763
  ]);
@@ -12618,8 +12906,8 @@ const EmptyData = {};
12618
12906
  className: "flex justify-between mb-2 ml-2",
12619
12907
  children: [
12620
12908
  /*#__PURE__*/ jsxRuntime.jsx(DownloadsPanel, {
12621
- dropdowns: dropdowns ?? {},
12622
- buttons: buttons ?? [],
12909
+ dropdowns: defaultDropdowns,
12910
+ buttons: defaultButtons,
12623
12911
  loginForDownload: loginForDownload,
12624
12912
  index: index,
12625
12913
  totalCount: counts ?? 0,
@@ -12638,7 +12926,8 @@ const EmptyData = {};
12638
12926
  ...chartsSection,
12639
12927
  charts: summaryCharts
12640
12928
  },
12641
- data: chartData ?? EmptyData
12929
+ data: chartData ?? EmptyData,
12930
+ isSuccess: isChartSuccess
12642
12931
  }) : /*#__PURE__*/ jsxRuntime.jsx(Charts, {
12643
12932
  charts: summaryCharts,
12644
12933
  data: chartData ?? EmptyData,
@@ -12692,6 +12981,9 @@ const TabsLayoutToComponentProp = (tabsLayout)=>{
12692
12981
  const CohortBuilder = ({ explorerConfig, sharedFiltersMap = null, tabsLayout = 'left' })=>{
12693
12982
  const dispatch = core.useCoreDispatch();
12694
12983
  dispatch(core.setSharedFilters(sharedFiltersMap ?? {}));
12984
+ const configuration = useDeepCompare.useDeepCompareMemo(()=>explorerConfig, [
12985
+ explorerConfig
12986
+ ]);
12695
12987
  return /*#__PURE__*/ jsxRuntime.jsx("div", {
12696
12988
  className: "w-full",
12697
12989
  children: /*#__PURE__*/ jsxRuntime.jsxs(core$1.Tabs, {
@@ -12702,17 +12994,24 @@ const CohortBuilder = ({ explorerConfig, sharedFiltersMap = null, tabsLayout = '
12702
12994
  /*#__PURE__*/ jsxRuntime.jsx(core$1.Tabs.List, {
12703
12995
  className: "w-full",
12704
12996
  justify: TabsLayoutToComponentProp(tabsLayout),
12705
- children: explorerConfig.map((panelConfig)=>/*#__PURE__*/ jsxRuntime.jsx(core$1.Tabs.Tab, {
12997
+ children: configuration.map((panelConfig)=>/*#__PURE__*/ jsxRuntime.jsx(core$1.Tabs.Tab, {
12706
12998
  value: panelConfig.tabTitle,
12707
12999
  children: panelConfig.tabTitle
12708
13000
  }, `${panelConfig.tabTitle}-tabList`))
12709
13001
  }),
12710
- explorerConfig.map((panelConfig)=>/*#__PURE__*/ jsxRuntime.jsx(core$1.Tabs.Panel, {
13002
+ configuration.map((panelConfig)=>/*#__PURE__*/ jsxRuntime.jsx(core$1.Tabs.Panel, {
12711
13003
  value: panelConfig.tabTitle,
12712
- children: /*#__PURE__*/ React.createElement(CohortPanel, {
12713
- ...panelConfig,
12714
- key: `${panelConfig.tabTitle}-CohortPanel`
12715
- })
13004
+ children: /*#__PURE__*/ jsxRuntime.jsx(CohortPanel, {
13005
+ guppyConfig: panelConfig.guppyConfig,
13006
+ chartsSection: panelConfig?.chartsSection,
13007
+ filters: panelConfig.filters,
13008
+ tabTitle: panelConfig.tabTitle,
13009
+ table: panelConfig.table,
13010
+ dropdowns: panelConfig.dropdowns,
13011
+ buttons: panelConfig.buttons,
13012
+ loginForDownload: panelConfig.loginForDownload,
13013
+ sharedFiltersMap: panelConfig.sharedFiltersMap
13014
+ }, `${panelConfig.tabTitle}-CohortPanel`)
12716
13015
  }, `${panelConfig.tabTitle}-tabPanel`))
12717
13016
  ]
12718
13017
  })
@@ -12832,6 +13131,18 @@ const TabbedCohortBuilder = ({ index, tabsConfiguration })=>{
12832
13131
  cohortFilters.root,
12833
13132
  isSuccess
12834
13133
  ]);
13134
+ const EnumHookInstances = {
13135
+ useGetFacetData: getEnumFacetData,
13136
+ useUpdateFacetFilters: lodash.partial(useUpdateFilters$1, index),
13137
+ useGetFacetFilters: lodash.partial(useGetFacetFilters$1, index),
13138
+ useClearFilter: lodash.partial(useClearFilters$1, index),
13139
+ useFilterExpanded: lodash.partial(useFilterExpandedState$1, index),
13140
+ useToggleExpandFilter: lodash.partial(useToggleExpandFilter$1, index),
13141
+ useGetCombineMode: lodash.partial(useCohortFilterCombineState, index),
13142
+ useSetCombineMode: lodash.partial(useSetCohortFilterCombineState, index),
13143
+ useFieldNameToTitle: useFieldNameToTitle,
13144
+ useTotalCounts: undefined
13145
+ };
12835
13146
  const RangeHookInstances = {
12836
13147
  useGetFacetData: getRangeFacetData,
12837
13148
  useUpdateFacetFilters: lodash.partial(useUpdateFilters$1, index),
@@ -12846,38 +13157,9 @@ const TabbedCohortBuilder = ({ index, tabsConfiguration })=>{
12846
13157
  const facetDataHooks = useDeepCompare.useDeepCompareMemo(()=>{
12847
13158
  return {
12848
13159
  // TODO: see if there a better way to do this
12849
- enum: {
12850
- useGetFacetData: getEnumFacetData,
12851
- useUpdateFacetFilters: lodash.partial(useUpdateFilters$1, index),
12852
- useGetFacetFilters: lodash.partial(useGetFacetFilters$1, index),
12853
- useClearFilter: lodash.partial(useClearFilters$1, index),
12854
- useFilterExpanded: lodash.partial(useFilterExpandedState$1, index),
12855
- useToggleExpandFilter: lodash.partial(useToggleExpandFilter$1, index),
12856
- useGetCombineMode: lodash.partial(useCohortFilterCombineState, index),
12857
- useSetCombineMode: lodash.partial(useSetCohortFilterCombineState, index),
12858
- useFieldNameToTitle: useFieldNameToTitle,
12859
- useTotalCounts: undefined
12860
- },
12861
- exact: {
12862
- useGetFacetData: getEnumFacetData,
12863
- useUpdateFacetFilters: lodash.partial(useUpdateFilters$1, index),
12864
- useGetFacetFilters: lodash.partial(useGetFacetFilters$1, index),
12865
- useClearFilter: lodash.partial(useClearFilters$1, index),
12866
- useFilterExpanded: lodash.partial(useFilterExpandedState$1, index),
12867
- useToggleExpandFilter: lodash.partial(useToggleExpandFilter$1, index),
12868
- useFieldNameToTitle: useFieldNameToTitle,
12869
- useTotalCounts: undefined
12870
- },
12871
- multiselect: {
12872
- useGetFacetData: getEnumFacetData,
12873
- useUpdateFacetFilters: lodash.partial(useUpdateFilters$1, index),
12874
- useGetFacetFilters: lodash.partial(useGetFacetFilters$1, index),
12875
- useClearFilter: lodash.partial(useClearFilters$1, index),
12876
- useFilterExpanded: lodash.partial(useFilterExpandedState$1, index),
12877
- useToggleExpandFilter: lodash.partial(useToggleExpandFilter$1, index),
12878
- useFieldNameToTitle: useFieldNameToTitle,
12879
- useTotalCounts: undefined
12880
- },
13160
+ enum: EnumHookInstances,
13161
+ exact: EnumHookInstances,
13162
+ multiselect: EnumHookInstances,
12881
13163
  range: RangeHookInstances,
12882
13164
  age: RangeHookInstances,
12883
13165
  year: RangeHookInstances,
@@ -12885,7 +13167,8 @@ const TabbedCohortBuilder = ({ index, tabsConfiguration })=>{
12885
13167
  days: RangeHookInstances,
12886
13168
  percent: RangeHookInstances,
12887
13169
  datetime: RangeHookInstances,
12888
- toggle: RangeHookInstances
13170
+ toggle: RangeHookInstances,
13171
+ upload: EnumHookInstances
12889
13172
  };
12890
13173
  }, [
12891
13174
  getEnumFacetData,
@@ -13843,47 +14126,25 @@ const Workspace = ({ config })=>{
13843
14126
  };
13844
14127
 
13845
14128
  const TextDescription = ({ description })=>{
13846
- const [extend, setExtend] = React.useState(false);
13847
- const textRef = React.useRef(null);
13848
- const [isClamped, setClamped] = React.useState(false);
13849
- React.useEffect(()=>{
13850
- // Function that should be called on window resize
13851
- function handleResize() {
13852
- if (textRef && textRef.current) {
13853
- setClamped(textRef.current.scrollHeight > textRef.current.clientHeight);
13854
- }
13855
- }
13856
- // Add event listener to window resize
13857
- window.addEventListener('resize', handleResize);
13858
- // Remove event listener on cleanup
13859
- return ()=>window.removeEventListener('resize', handleResize);
13860
- }, []); // Empty array ensures that it would only run on mount
13861
- return /*#__PURE__*/ jsxRuntime.jsxs(jsxRuntime.Fragment, {
13862
- children: [
13863
- !extend ? /*#__PURE__*/ jsxRuntime.jsx(core$1.Text, {
13864
- ref: textRef,
13865
- size: "sm",
13866
- lineClamp: 4,
13867
- children: description
13868
- }) : /*#__PURE__*/ jsxRuntime.jsx(core$1.Text, {
13869
- size: "sm",
13870
- children: description
13871
- }),
13872
- isClamped && /*#__PURE__*/ jsxRuntime.jsx("button", {
13873
- onClick: ()=>setExtend((extend)=>!extend),
13874
- children: /*#__PURE__*/ jsxRuntime.jsxs("div", {
13875
- className: "flex text-xs font-semibold text-base-contrast-light",
13876
- children: [
13877
- !extend ? 'Extend Text' : 'Collapse Text',
13878
- ' ',
13879
- /*#__PURE__*/ jsxRuntime.jsx("div", {
13880
- className: "my-auto",
13881
- children: !extend ? /*#__PURE__*/ jsxRuntime.jsx(md.MdKeyboardArrowDown, {}) : /*#__PURE__*/ jsxRuntime.jsx(md.MdKeyboardArrowUp, {})
13882
- })
13883
- ]
14129
+ return /*#__PURE__*/ jsxRuntime.jsx(core$1.Spoiler, {
14130
+ maxHeight: 80,
14131
+ showLabel: /*#__PURE__*/ jsxRuntime.jsxs("span", {
14132
+ children: [
14133
+ "Extend Text ",
14134
+ /*#__PURE__*/ jsxRuntime.jsx(md.MdKeyboardArrowDown, {
14135
+ className: "inline"
13884
14136
  })
13885
- })
13886
- ]
14137
+ ]
14138
+ }),
14139
+ hideLabel: /*#__PURE__*/ jsxRuntime.jsxs("span", {
14140
+ children: [
14141
+ "Collapse Text ",
14142
+ /*#__PURE__*/ jsxRuntime.jsx(md.MdKeyboardArrowUp, {
14143
+ className: "inline"
14144
+ })
14145
+ ]
14146
+ }),
14147
+ children: description
13887
14148
  });
13888
14149
  };
13889
14150
 
@@ -13891,20 +14152,22 @@ const AnalysisCard = ({ title, description, type, icon, image, hasDemo, loginReq
13891
14152
  return /*#__PURE__*/ jsxRuntime.jsxs(core$1.Stack, {
13892
14153
  align: "stretch",
13893
14154
  justify: "space-between",
13894
- className: "rounded-sm rounded-t-md bg-base-max p-0",
14155
+ className: "rounded-sm rounded-t-md bg-base-max p-0 h-full",
13895
14156
  children: [
13896
14157
  /*#__PURE__*/ jsxRuntime.jsxs("div", {
13897
- className: "h-full",
14158
+ className: "relative",
13898
14159
  children: [
13899
14160
  /*#__PURE__*/ jsxRuntime.jsx("div", {
13900
- className: "p-0 rounded-sm h-1/2 h-max-1/2",
13901
- children: /*#__PURE__*/ jsxRuntime.jsx(core$1.Image, {
13902
- component: Image,
13903
- src: `${image}`,
13904
- alt: `${title} image`,
13905
- height: 1000,
13906
- width: 1000,
13907
- radius: "md"
14161
+ className: "p-0 rounded-sm h-[200px] h-max-1/2 flex justify-center items-center relative overflow-hidden",
14162
+ children: /*#__PURE__*/ jsxRuntime.jsx("div", {
14163
+ children: /*#__PURE__*/ jsxRuntime.jsx(core$1.Image, {
14164
+ component: Image,
14165
+ src: `${image}`,
14166
+ alt: "",
14167
+ radius: "md",
14168
+ width: 500,
14169
+ height: 500
14170
+ })
13908
14171
  })
13909
14172
  }),
13910
14173
  /*#__PURE__*/ jsxRuntime.jsxs("div", {
@@ -13915,7 +14178,7 @@ const AnalysisCard = ({ title, description, type, icon, image, hasDemo, loginReq
13915
14178
  children: /*#__PURE__*/ jsxRuntime.jsx(core$1.Image, {
13916
14179
  component: Image,
13917
14180
  src: `${icon}`,
13918
- alt: `${title} logo`,
14181
+ alt: "",
13919
14182
  width: 40,
13920
14183
  height: 40,
13921
14184
  radius: "lg"
@@ -16959,7 +17222,7 @@ const registerCohortDiscoveryApp = ()=>core.createGen3AppWithOwnStore({
16959
17222
  App: CohortDiscovery,
16960
17223
  id: AppId$1,
16961
17224
  name: _APP_NAME$2,
16962
- version: 'v1.0.0',
17225
+ version: _APP_VERSION$1,
16963
17226
  requiredEntityTypes: [],
16964
17227
  store: AppStore,
16965
17228
  context: AppContext
@@ -19151,6 +19414,98 @@ const registerMetadataSchemaApp = ()=>core.createGen3App({
19151
19414
  requiredEntityTypes: []
19152
19415
  });
19153
19416
 
19417
+ const ADDITIONAL_DOWNLOAD_MESSAGE = 'A previous download is being processed. Additional downloads may be started.';
19418
+ const DropdownWithIcon = ({ disableTargetWidth, LeftSection, RightSection = /*#__PURE__*/ jsxRuntime.jsx("div", {
19419
+ className: "border-l pl-1 -mr-2",
19420
+ children: /*#__PURE__*/ jsxRuntime.jsx(io.IoMdArrowDropdown, {
19421
+ size: "1.25em",
19422
+ "aria-hidden": "true",
19423
+ "data-testid": "dropdown-icon"
19424
+ })
19425
+ }), TargetButtonChildren, targetButtonDisabled, dropdownElements, menuLabelText, menuLabelCustomClass, customPosition, fullHeight, zIndex = 900, customTargetButtonDataTestId = undefined, targetButtonTooltip = undefined, buttonAriaLabel = undefined, closeOnItemClick = true })=>{
19426
+ const targetRef = React.useRef(null);
19427
+ return /*#__PURE__*/ jsxRuntime.jsxs(core$1.Menu, {
19428
+ width: !disableTargetWidth ? 'target' : null,
19429
+ ...customPosition && {
19430
+ position: customPosition
19431
+ },
19432
+ zIndex: zIndex,
19433
+ closeOnItemClick: closeOnItemClick,
19434
+ children: [
19435
+ /*#__PURE__*/ jsxRuntime.jsx(core$1.Menu.Target, {
19436
+ children: /*#__PURE__*/ jsxRuntime.jsx(core$1.Tooltip, {
19437
+ label: targetButtonTooltip,
19438
+ disabled: !targetButtonTooltip,
19439
+ children: /*#__PURE__*/ jsxRuntime.jsx(core$1.Button, {
19440
+ variant: "outline",
19441
+ color: "primary",
19442
+ className: `flex items-center bg-base-max border-primary data-disabled:opacity-50 data-disabled:bg-base-max data-disabled:text-primary ${focusStyles}`,
19443
+ ...LeftSection && {
19444
+ leftSection: LeftSection
19445
+ },
19446
+ rightSection: RightSection,
19447
+ disabled: targetButtonDisabled,
19448
+ classNames: {
19449
+ root: `${fullHeight ? 'h-full' : undefined}`
19450
+ },
19451
+ ref: targetRef,
19452
+ "aria-label": buttonAriaLabel,
19453
+ "data-testid": customTargetButtonDataTestId ?? 'menu-elem',
19454
+ children: TargetButtonChildren
19455
+ })
19456
+ })
19457
+ }),
19458
+ /*#__PURE__*/ jsxRuntime.jsxs(core$1.Menu.Dropdown, {
19459
+ "data-testid": "dropdown-menu-options",
19460
+ className: "border-1 border-secondary",
19461
+ children: [
19462
+ menuLabelText && /*#__PURE__*/ jsxRuntime.jsxs(jsxRuntime.Fragment, {
19463
+ children: [
19464
+ /*#__PURE__*/ jsxRuntime.jsx(core$1.Menu.Label, {
19465
+ className: menuLabelCustomClass ?? 'font-bold',
19466
+ "data-testid": "menu-label",
19467
+ children: menuLabelText
19468
+ }),
19469
+ /*#__PURE__*/ jsxRuntime.jsx(core$1.Menu.Divider, {})
19470
+ ]
19471
+ }),
19472
+ dropdownElements.map(({ title, onClick, icon, disabled, isLoading, loadingTooltip }, idx)=>{
19473
+ const menuItem = /*#__PURE__*/ jsxRuntime.jsx(core$1.Menu.Item, {
19474
+ onClick: ()=>{
19475
+ if (onClick) {
19476
+ onClick();
19477
+ }
19478
+ // This is done inorder to set the last focused element as the menu target element
19479
+ // This is done to return focus to the target element if the modal is closed with ESC
19480
+ if (targetRef?.current) {
19481
+ targetRef?.current?.focus();
19482
+ }
19483
+ },
19484
+ "data-testid": `${title}-${idx}`,
19485
+ leftSection: icon && icon,
19486
+ disabled: disabled,
19487
+ children: title
19488
+ }, `${title}-${idx}`);
19489
+ if (isLoading) {
19490
+ return /*#__PURE__*/ jsxRuntime.jsx(core$1.Tooltip, {
19491
+ label: loadingTooltip || ADDITIONAL_DOWNLOAD_MESSAGE,
19492
+ position: "right",
19493
+ withArrow: true,
19494
+ multiline: true,
19495
+ w: 400,
19496
+ children: /*#__PURE__*/ jsxRuntime.jsx("div", {
19497
+ children: menuItem
19498
+ })
19499
+ }, `${title}-${idx}`);
19500
+ }
19501
+ return menuItem;
19502
+ })
19503
+ ]
19504
+ })
19505
+ ]
19506
+ });
19507
+ };
19508
+
19154
19509
  const ActionButton = ({ title, enabled, type, leftIcon, rightIcon, tooltipText })=>{
19155
19510
  return /*#__PURE__*/ jsxRuntime.jsx(core$1.Tooltip, {
19156
19511
  label: tooltipText,
@@ -25612,6 +25967,7 @@ const staticNotebookAPI = async (req, res)=>{
25612
25967
 
25613
25968
  exports.AISearchPageGetServerSideProps = AISearchPageGetServerSideProps;
25614
25969
  exports.AccessLevel = AccessLevel;
25970
+ exports.AccordionPanel = AccordionPanel;
25615
25971
  exports.ActionBar = ActionBar;
25616
25972
  exports.ActionButton = ActionButton;
25617
25973
  exports.AdminAuthZPageGetServerSideProps = AdminAuthZPageGetServerSideProps;
@@ -25654,6 +26010,8 @@ exports.DiscoveryPage = DiscoveryPage;
25654
26010
  exports.DiscoveryPageGetServerSideProps = DiscoveryPageGetServerSideProps;
25655
26011
  exports.DiscoveryRowRendererFactory = DiscoveryRowRendererFactory;
25656
26012
  exports.DropdownButton = DropdownButton;
26013
+ exports.DropdownPanel = DropdownPanel;
26014
+ exports.DropdownWithIcon = DropdownWithIcon;
25657
26015
  exports.EnumFacet = EnumFacet;
25658
26016
  exports.EnumFacetChart = EnumFacetChart;
25659
26017
  exports.ErrorCard = ErrorCard;
@@ -25668,6 +26026,7 @@ exports.FacetExpander = FacetExpander;
25668
26026
  exports.FacetSelector = FacetSelector;
25669
26027
  exports.FacetSortPanel = FacetSortPanel;
25670
26028
  exports.FacetTabs = FacetTabs;
26029
+ exports.FiltersPanel = FiltersPanel;
25671
26030
  exports.FirstTimeModal = FirstTimeModal;
25672
26031
  exports.Footer = Footer;
25673
26032
  exports.Gen3Button = Gen3Button;
@@ -25706,6 +26065,7 @@ exports.RangeFacet = RangeFacet;
25706
26065
  exports.ReactECharts = ReactECharts;
25707
26066
  exports.ResourcesFilters = ResourcesFilters;
25708
26067
  exports.SPECIAL_CASE_FIELDS = SPECIAL_CASE_FIELDS;
26068
+ exports.SegmentedControl = SegmentedControl;
25709
26069
  exports.SessionExpiredModal = SessionExpiredModal;
25710
26070
  exports.SinglePageStudyDetailsPanel = SinglePageStudyDetailsPanel;
25711
26071
  exports.StaticNotebookIFrame = StaticNotebookIFrame;
@@ -25719,6 +26079,7 @@ exports.SubmissionPageGetServerSideProps = SubmissionPageGetServerSideProps;
25719
26079
  exports.TabbedCohortBuilder = TabbedCohortBuilder;
25720
26080
  exports.TabbedCohortBuilderPage = TabbedCohortBuilderPage;
25721
26081
  exports.TabbedCohortBuilderPageGetServerSideProps = TabbedCohortBuilderPageGetServerSideProps;
26082
+ exports.TabbedPanel = TabbedPanel;
25722
26083
  exports.TagCloud = TagCloud;
25723
26084
  exports.TailwindConfig = TailwindConfig;
25724
26085
  exports.TopBar = TopBar;