@rh-support/cases 2.4.10-beta.6 → 2.5.0

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 (130) hide show
  1. package/README.md +2 -0
  2. package/lib/esm/components/case/NewCaseButton.d.ts +2 -1
  3. package/lib/esm/components/case/NewCaseButton.d.ts.map +1 -1
  4. package/lib/esm/components/case-list/CaseList.d.ts +4 -3
  5. package/lib/esm/components/case-list/CaseList.d.ts.map +1 -1
  6. package/lib/esm/components/case-list/CaseList.js +42 -44
  7. package/lib/esm/components/case-list/CaseListContext.d.ts +1 -1
  8. package/lib/esm/components/case-list/CaseListContext.d.ts.map +1 -1
  9. package/lib/esm/components/case-list/CaseListFilterContext.d.ts +1 -1
  10. package/lib/esm/components/case-list/CaseListFilterContext.d.ts.map +1 -1
  11. package/lib/esm/components/case-list/CaseListFilterHelpers.d.ts.map +1 -1
  12. package/lib/esm/components/case-list/CaseListFilterReducer.d.ts +6 -3
  13. package/lib/esm/components/case-list/CaseListFilterReducer.d.ts.map +1 -1
  14. package/lib/esm/components/case-list/CaseListFilterReducer.js +3 -0
  15. package/lib/esm/components/case-list/CaseListReducer.d.ts +2 -2
  16. package/lib/esm/components/case-list/CaseListReducer.d.ts.map +1 -1
  17. package/lib/esm/components/case-list/case-list-filters/AccountsBookmarkedGroupFilter.d.ts +3 -2
  18. package/lib/esm/components/case-list/case-list-filters/AccountsBookmarkedGroupFilter.d.ts.map +1 -1
  19. package/lib/esm/components/case-list/case-list-filters/AccountsBookmarkedGroupFilter.js +25 -11
  20. package/lib/esm/components/case-list/case-list-filters/AccountsFilter.d.ts +2 -1
  21. package/lib/esm/components/case-list/case-list-filters/AccountsFilter.d.ts.map +1 -1
  22. package/lib/esm/components/case-list/case-list-filters/AccountsFilter.js +10 -5
  23. package/lib/esm/components/case-list/case-list-filters/AdditionalFilters.d.ts +2 -1
  24. package/lib/esm/components/case-list/case-list-filters/AdditionalFilters.d.ts.map +1 -1
  25. package/lib/esm/components/case-list/case-list-filters/AdditionalFilters.js +19 -4
  26. package/lib/esm/components/case-list/case-list-filters/CaseListFilterChips.d.ts +2 -1
  27. package/lib/esm/components/case-list/case-list-filters/CaseListFilterChips.d.ts.map +1 -1
  28. package/lib/esm/components/case-list/case-list-filters/CaseListFilterChips.js +1 -1
  29. package/lib/esm/components/case-list/case-list-filters/CaseListFilters.d.ts +2 -1
  30. package/lib/esm/components/case-list/case-list-filters/CaseListFilters.d.ts.map +1 -1
  31. package/lib/esm/components/case-list/case-list-filters/CreatorSsoNameFilter.d.ts +12 -1
  32. package/lib/esm/components/case-list/case-list-filters/CreatorSsoNameFilter.d.ts.map +1 -1
  33. package/lib/esm/components/case-list/case-list-filters/CreatorSsoNameFilter.js +139 -163
  34. package/lib/esm/components/case-list/case-list-filters/CreatorSsoNameFilterChip.d.ts +2 -1
  35. package/lib/esm/components/case-list/case-list-filters/CreatorSsoNameFilterChip.d.ts.map +1 -1
  36. package/lib/esm/components/case-list/case-list-filters/CreatorSsoNameFilterChip.js +1 -1
  37. package/lib/esm/components/case-list/case-list-filters/GroupsFilter.d.ts +2 -1
  38. package/lib/esm/components/case-list/case-list-filters/GroupsFilter.d.ts.map +1 -1
  39. package/lib/esm/components/case-list/case-list-filters/GroupsFilter.js +157 -27
  40. package/lib/esm/components/case-list/case-list-filters/InternalSsoNameFilter.d.ts +3 -0
  41. package/lib/esm/components/case-list/case-list-filters/InternalSsoNameFilter.d.ts.map +1 -0
  42. package/lib/esm/components/case-list/case-list-filters/InternalSsoNameFilter.js +207 -0
  43. package/lib/esm/components/case-list/case-list-filters/ProductFilterChip.d.ts +2 -1
  44. package/lib/esm/components/case-list/case-list-filters/ProductFilterChip.d.ts.map +1 -1
  45. package/lib/esm/components/case-list/case-list-filters/ProductFilterChip.js +1 -1
  46. package/lib/esm/components/case-list/case-list-filters/ProductsFilter.d.ts +2 -1
  47. package/lib/esm/components/case-list/case-list-filters/ProductsFilter.d.ts.map +1 -1
  48. package/lib/esm/components/case-list/case-list-filters/ProductsFilter.js +7 -5
  49. package/lib/esm/components/case-list/case-list-filters/SeverityFilter.d.ts +2 -1
  50. package/lib/esm/components/case-list/case-list-filters/SeverityFilter.d.ts.map +1 -1
  51. package/lib/esm/components/case-list/case-list-filters/SeverityFilter.js +4 -4
  52. package/lib/esm/components/case-list/case-list-filters/StatusFilter.d.ts +2 -1
  53. package/lib/esm/components/case-list/case-list-filters/StatusFilter.d.ts.map +1 -1
  54. package/lib/esm/components/case-list/case-list-filters/StatusFilter.js +4 -4
  55. package/lib/esm/components/case-list/case-list-filters/TypeFilter.d.ts +2 -1
  56. package/lib/esm/components/case-list/case-list-filters/TypeFilter.d.ts.map +1 -1
  57. package/lib/esm/components/case-list/case-list-filters/TypeFilter.js +3 -3
  58. package/lib/esm/components/case-list/case-list-filters/VersionsFilter.d.ts +2 -1
  59. package/lib/esm/components/case-list/case-list-filters/VersionsFilter.d.ts.map +1 -1
  60. package/lib/esm/components/case-list/case-list-filters/VersionsFilter.js +35 -4
  61. package/lib/esm/components/case-list/case-list-table/CaseListTable.d.ts +2 -1
  62. package/lib/esm/components/case-list/case-list-table/CaseListTable.d.ts.map +1 -1
  63. package/lib/esm/components/case-list/case-list-table/CaseListTable.js +211 -113
  64. package/lib/esm/components/case-list/case-list-table/CloseCaseBtn.d.ts +2 -1
  65. package/lib/esm/components/case-list/case-list-table/CloseCaseBtn.d.ts.map +1 -1
  66. package/lib/esm/components/case-list/case-list-table/CloseCaseBtn.js +7 -2
  67. package/lib/esm/components/case-list/case-list-table/DownloadCSVFileModal.d.ts +19 -0
  68. package/lib/esm/components/case-list/case-list-table/DownloadCSVFileModal.d.ts.map +1 -0
  69. package/lib/esm/components/case-list/case-list-table/DownloadCSVFileModal.js +296 -0
  70. package/lib/esm/components/case-list/case-list-table/DownloadCSVFileModal.scss +27 -0
  71. package/lib/esm/components/case-list/case-list-table/ExportCaseListCSV.d.ts +3 -1
  72. package/lib/esm/components/case-list/case-list-table/ExportCaseListCSV.d.ts.map +1 -1
  73. package/lib/esm/components/case-list/case-list-table/ExportCaseListCSV.js +19 -96
  74. package/lib/esm/components/case-list/case-list-table/SeverityLabel.d.ts +2 -1
  75. package/lib/esm/components/case-list/case-list-table/SeverityLabel.d.ts.map +1 -1
  76. package/lib/esm/components/case-list/case-list-table/table-column-selector/TableColumnSelector.d.ts +9 -0
  77. package/lib/esm/components/case-list/case-list-table/table-column-selector/TableColumnSelector.d.ts.map +1 -0
  78. package/lib/esm/components/case-list/case-list-table/table-column-selector/TableColumnSelector.js +53 -0
  79. package/lib/esm/components/case-list/case-list-table/table-column-selector/TableColumnSelector.scss +7 -0
  80. package/lib/esm/components/case-list/case-search/AdvanceSearch.d.ts +2 -1
  81. package/lib/esm/components/case-list/case-search/AdvanceSearch.d.ts.map +1 -1
  82. package/lib/esm/components/case-list/case-search/AdvanceSearch.js +18 -13
  83. package/lib/esm/components/case-list/case-search/BookmarkedSearchesSelector.d.ts +2 -1
  84. package/lib/esm/components/case-list/case-search/BookmarkedSearchesSelector.d.ts.map +1 -1
  85. package/lib/esm/components/case-list/case-search/BookmarkedSearchesSelector.js +7 -6
  86. package/lib/esm/components/case-list/case-search/CaseSearch.d.ts +2 -1
  87. package/lib/esm/components/case-list/case-search/CaseSearch.d.ts.map +1 -1
  88. package/lib/esm/components/case-list/case-search/CaseSearch.js +2 -2
  89. package/lib/esm/components/case-list/case-search/SaveCaseSearchModal.d.ts +2 -1
  90. package/lib/esm/components/case-list/case-search/SaveCaseSearchModal.d.ts.map +1 -1
  91. package/lib/esm/components/case-list/case-search/SaveCaseSearchModal.js +48 -40
  92. package/lib/esm/components/case-list/case-search/useAdvanceSearchParser.js +1 -1
  93. package/lib/esm/components/escalations/EscalationForm.d.ts +1 -1
  94. package/lib/esm/components/escalations/EscalationForm.d.ts.map +1 -1
  95. package/lib/esm/components/escalations/EscalationForm.js +18 -9
  96. package/lib/esm/components/escalations/PartnerEscalation.d.ts +2 -1
  97. package/lib/esm/components/escalations/PartnerEscalation.d.ts.map +1 -1
  98. package/lib/esm/components/index.d.ts +2 -8
  99. package/lib/esm/components/index.d.ts.map +1 -1
  100. package/lib/esm/components/index.js +5 -8
  101. package/lib/esm/css/caseList.css +85 -64
  102. package/lib/esm/css/caseSearch.css +1 -1
  103. package/lib/esm/css/escalation.css +4 -4
  104. package/lib/esm/enums/cache.d.ts +1 -1
  105. package/lib/esm/enums/cache.d.ts.map +1 -1
  106. package/lib/esm/enums/case.js +1 -1
  107. package/lib/esm/enums/filters.d.ts +1 -1
  108. package/lib/esm/enums/filters.d.ts.map +1 -1
  109. package/lib/esm/enums/filters.js +1 -1
  110. package/lib/esm/i18n/template-es.js +1 -1
  111. package/lib/esm/index.d.ts +0 -2
  112. package/lib/esm/index.d.ts.map +1 -1
  113. package/lib/esm/index.js +0 -2
  114. package/lib/esm/models/caseList.d.ts +5 -2
  115. package/lib/esm/models/caseList.d.ts.map +1 -1
  116. package/lib/esm/scss/_main.scss +11 -11
  117. package/lib/esm/scss/_pf-overrides.scss +40 -4
  118. package/lib/esm/scss/index.scss +0 -1
  119. package/lib/esm/test-utils/testSetup.d.ts +1 -1
  120. package/lib/esm/test-utils/testSetup.d.ts.map +1 -1
  121. package/lib/esm/test-utils/testSetup.js +1 -1
  122. package/lib/esm/test-utils/testUtils.d.ts +1 -1
  123. package/lib/esm/test-utils/testUtils.js +1 -1
  124. package/lib/esm/utils/caseListUtils.js +3 -3
  125. package/lib/esm/utils/caseSearchUtils.d.ts +3 -3
  126. package/lib/esm/utils/caseSearchUtils.d.ts.map +1 -1
  127. package/lib/esm/utils/caseSearchUtils.js +18 -5
  128. package/lib/esm/utils/constants.js +1 -1
  129. package/lib/esm/utils/routeUtils.js +2 -1
  130. package/package.json +35 -32
@@ -1,12 +1,15 @@
1
- import { Bullseye, Button, EmptyState, EmptyStateBody, EmptyStateIcon, EmptyStateVariant, PaginationVariant, Title, } from '@patternfly/react-core';
1
+ import { Bullseye, Button, EmptyState, EmptyStateBody, EmptyStateFooter, EmptyStateHeader, EmptyStateIcon, EmptyStateVariant, PaginationVariant, Spinner, } from '@patternfly/react-core';
2
2
  import SearchIcon from '@patternfly/react-icons/dist/js/icons/search-icon';
3
- import { PFTable, Table, TableColumnSelector, TablePagination, } from '@rh-support/components';
4
- import { GlobalMetadataDispatchContext, GlobalMetadataStateContext, updateUserPreferences, useGlobalStateContext, UserPreferencesKeys, } from '@rh-support/react-context';
3
+ import { Table, TableVariant, Tbody, Td, Th, Thead, Tr, Visibility } from '@patternfly/react-table';
4
+ import { TableComponent, TablePagination } from '@rh-support/components';
5
+ import { GlobalMetadataDispatchContext, updateUserPreferences, useGlobalStateContext, UserPreferencesKeys, } from '@rh-support/react-context';
5
6
  import { formatDate, scrollIntoView, toNewCaseTypeSwitcher } from '@rh-support/utils';
6
7
  import find from 'lodash/find';
7
8
  import flatMap from 'lodash/flatMap';
8
- import get from 'lodash/get';
9
9
  import includes from 'lodash/includes';
10
+ import isEmpty from 'lodash/isEmpty';
11
+ import isEqual from 'lodash/isEqual';
12
+ import isUndefined from 'lodash/isUndefined';
10
13
  import React, { useContext, useEffect, useRef, useState } from 'react';
11
14
  import { Trans, useTranslation } from 'react-i18next';
12
15
  import { Link } from 'react-router-dom';
@@ -16,6 +19,8 @@ import { clearFilters, resetFilterToDefaultState, updatePagination, updateSort,
16
19
  import CloseCaseBtn from './CloseCaseBtn';
17
20
  import { ExportCaseListCSV } from './ExportCaseListCSV';
18
21
  import SeverityLabel from './SeverityLabel';
22
+ import { TableColumnSelector } from './table-column-selector/TableColumnSelector';
23
+ // initially selected columns
19
24
  const initialSelectedColumns = [
20
25
  CaseListColumnIds.caseId,
21
26
  CaseListColumnIds.summary,
@@ -29,163 +34,114 @@ const EMPTY_STATE_NO_FILTERS = 'The table will be populated after creating your
29
34
  const EMPTY_STATE_NO_FILTERS_INTERNALUSER = 'Try expanding your search to filter on cases for all Red Hat accounts.';
30
35
  const EMPTY_STATE_NO_FILTERS_ERROR = (React.createElement(React.Fragment, null,
31
36
  "Try refreshing or check the",
32
- ' ',
33
37
  React.createElement("a", { href: "https://status.redhat.com/", target: "_blank", rel: "noopener noreferrer" }, "status page"),
34
38
  "to see if there are any known issues"));
35
39
  export function CaseListTable(props) {
36
40
  var _a, _b, _c, _d, _e, _f;
37
- const [selectedColumns, setSelectedColumns] = useState(initialSelectedColumns);
41
+ const [selectedColumns, setSelectedColumns] = useState([]);
38
42
  const { t } = useTranslation();
39
43
  const [selectedCases, setSelectedCases] = useState([]);
40
44
  const caseListData = props.isCaseListPageLoading ? [] : (_b = (_a = props.caseList) === null || _a === void 0 ? void 0 : _a.docs) !== null && _b !== void 0 ? _b : [];
41
45
  const isColumnVisible = (columnId) => {
42
46
  return includes(selectedColumns, columnId);
43
47
  };
44
- const { globalMetadataState: { navBarRef, hydraUserPreferences }, } = useGlobalStateContext();
48
+ const mandatoryColumns = ['number', 'summary'];
49
+ const visibleColumns = mandatoryColumns.concat(selectedColumns);
50
+ const [activeSortIndex, setActiveSortIndex] = useState();
51
+ const [activeSortDirection, setActiveSortDirection] = useState();
52
+ const [sortedCaseListData, setSortedCaseListData] = useState(caseListData);
53
+ const { globalMetadataState: { navBarRef, hydraUserPreferences, loggedInUserRights }, } = useGlobalStateContext();
45
54
  const dispatch = useContext(CaseListFilterDispatchContext);
46
55
  const dispatchToGlobalMetadataReducer = useContext(GlobalMetadataDispatchContext);
47
- const { filterInfo } = useContext(CaseListFilterStateContext);
56
+ const { filterInfo, filterQueryInfo } = useContext(CaseListFilterStateContext);
48
57
  const currentFilterLength = flatMap(filterInfo).length;
49
58
  const showingFilter = currentFilterLength > 0;
50
- const filterState = useContext(CaseListFilterStateContext);
51
- const { filterQueryInfo } = filterState;
52
- const hasSearchQuery = !(filterQueryInfo.queryString === '');
53
- const { globalMetadataState: { loggedInUserRights }, } = useContext(GlobalMetadataStateContext);
59
+ const hasSearchQuery = !((filterQueryInfo === null || filterQueryInfo === void 0 ? void 0 : filterQueryInfo.queryString) === '');
54
60
  const isInternal = loggedInUserRights.data.isInternal();
55
61
  const tableToolbarRef = useRef(null);
56
- const getCaseGroupName = (groupNum) => {
57
- if (!groupNum || props.caseGroups.length < 1)
58
- return '';
59
- const group = props.caseGroups.find((group) => group.groupNum === groupNum);
60
- return (group === null || group === void 0 ? void 0 : group.name) || '';
61
- };
62
62
  const columns = [
63
63
  {
64
64
  id: CaseListColumnIds.caseId,
65
- cellWidth: 10,
66
65
  title: t('Case ID'),
67
- rowProps: (data) => ({ 'data-casenumber': data.case_number }),
68
66
  sortable: true,
69
- cell: (data) => (React.createElement(React.Fragment, null,
70
- React.createElement(Link, { to: `/case/${data.case_number}` },
71
- React.createElement("span", { className: "case-number" }, data.case_number)),
72
- ' ',
73
- data.case_customer_escalation ? (React.createElement("div", { className: "escalation-label" },
74
- React.createElement(Trans, null, "Escalated"))) : null)),
75
67
  },
76
68
  {
77
69
  id: CaseListColumnIds.summary,
78
- cellWidth: 10,
79
- title: t('Issue summary'),
70
+ title: t('Title'),
80
71
  sortable: true,
81
- accessor: (data) => data.case_summary,
82
72
  },
83
73
  {
84
74
  id: CaseListColumnIds.owner,
85
- cellWidth: 10,
86
75
  title: t('Owner'),
87
76
  sortable: true,
88
- accessor: (data) => data.case_contactName,
89
77
  show: isColumnVisible(CaseListColumnIds.owner),
90
78
  },
91
79
  {
92
80
  id: CaseListColumnIds.modified,
93
- cellWidth: 10,
94
81
  title: t('Modified by'),
95
82
  sortable: true,
96
- cell: (data) => (React.createElement(React.Fragment, null,
97
- React.createElement("span", { className: "modified-name" }, data.case_lastModifiedByName),
98
- ' ',
99
- data.case_lastModifiedDate ? formatDate(data.case_lastModifiedDate) : null)),
100
83
  show: isColumnVisible(CaseListColumnIds.modified),
101
84
  },
102
85
  {
103
86
  id: CaseListColumnIds.severity,
104
- cellWidth: 10,
105
87
  title: t('Severity'),
106
88
  sortable: true,
107
- cell: (data) => React.createElement(SeverityLabel, { sevValue: data.case_severity }),
108
89
  show: isColumnVisible(CaseListColumnIds.severity),
109
90
  },
110
91
  {
111
92
  id: CaseListColumnIds.status,
112
- cellWidth: 10,
113
93
  title: t('Status'),
114
94
  sortable: true,
115
- accessor: (data) => data.case_status,
116
95
  show: isColumnVisible(CaseListColumnIds.status),
117
96
  },
118
97
  {
119
98
  id: CaseListColumnIds.created,
120
- cellWidth: 10,
121
99
  title: t('Created by'),
122
100
  sortable: true,
123
- cell: (data) => (React.createElement(React.Fragment, null,
124
- React.createElement("span", { className: "created-name" }, data.case_createdByName),
125
- ' ',
126
- data.case_createdDate ? formatDate(data.case_createdDate) : null)),
127
101
  show: isColumnVisible(CaseListColumnIds.created),
128
102
  },
129
103
  {
130
104
  id: CaseListColumnIds.productAndVersion,
131
105
  cellWidth: 15,
132
106
  title: t('Product and version'),
133
- cell: (data) => (React.createElement(React.Fragment, null,
134
- data.case_product,
135
- " ",
136
- React.createElement("span", { style: { display: 'block' } }, data.case_version))),
137
107
  show: isColumnVisible(CaseListColumnIds.productAndVersion),
138
108
  },
139
109
  {
140
110
  id: CaseListColumnIds.accountNumber,
141
- cellWidth: 10,
142
111
  title: t('Account number'),
143
112
  sortable: true,
144
- accessor: (data) => data.case_accountNumber,
145
113
  show: isColumnVisible(CaseListColumnIds.accountNumber),
146
114
  },
147
115
  {
148
116
  id: CaseListColumnIds.alternateCaseId,
149
- cellWidth: 10,
150
117
  title: t('Personal reference number'),
151
118
  sortable: true,
152
- accessor: (data) => data.case_alternate_id,
153
119
  show: isColumnVisible(CaseListColumnIds.alternateCaseId),
154
120
  },
155
121
  {
156
122
  id: CaseListColumnIds.type,
157
- cellWidth: 10,
158
123
  title: t('Support type'),
159
124
  sortable: true,
160
- accessor: (data) => toNewCaseTypeSwitcher(data.case_type),
161
125
  show: isColumnVisible(CaseListColumnIds.type),
162
126
  },
163
127
  {
164
128
  id: CaseListColumnIds.caseClosedDate,
165
- cellWidth: 10,
166
129
  title: t('Closed date'),
167
130
  sortable: true,
168
- accessor: (data) => formatDate(data.case_closedDate),
169
131
  show: isColumnVisible(CaseListColumnIds.caseClosedDate),
170
132
  },
171
133
  {
172
134
  id: CaseListColumnIds.group,
173
- cellWidth: 10,
174
135
  title: t('Group'),
175
136
  sortable: true,
176
- accessor: (data) => data.case_folderName || getCaseGroupName(data.case_folderNumber),
177
137
  show: isColumnVisible(CaseListColumnIds.group),
178
138
  },
179
139
  ];
180
- const getSelectedColumnsListFromCache = () => {
181
- const savedSelectedColumnsKey = UserPreferencesKeys.caseListSelectedColumns;
182
- const savedSelectedColumns = find(hydraUserPreferences.data, (pref) => pref.key === savedSelectedColumnsKey);
183
- (savedSelectedColumns === null || savedSelectedColumns === void 0 ? void 0 : savedSelectedColumns.value) && setSelectedColumns(JSON.parse(savedSelectedColumns.value));
140
+ const visibleCaseListColumns = columns.filter((column) => visibleColumns.includes(column.id));
141
+ const allRows = caseListData.map((row, index) => row.case_number);
142
+ const selectAllRows = () => {
143
+ !isEqual(selectedCases, allRows) ? setSelectedCases(allRows) : setSelectedCases([]);
184
144
  };
185
- useEffect(() => {
186
- getSelectedColumnsListFromCache();
187
- // eslint-disable-next-line react-hooks/exhaustive-deps
188
- }, []);
189
145
  const onColumnSelectorChange = (selectedColumnsList) => {
190
146
  setSelectedColumns(selectedColumnsList);
191
147
  try {
@@ -200,9 +156,6 @@ export function CaseListTable(props) {
200
156
  console.error('Could not save selected columns in cache');
201
157
  }
202
158
  };
203
- const onSortChange = (column, direction) => {
204
- updateSort(dispatch, { direction, column: column.id });
205
- };
206
159
  const onPerPageSelect = (paginationInfo) => {
207
160
  updatePagination(dispatch, paginationInfo);
208
161
  };
@@ -214,20 +167,12 @@ export function CaseListTable(props) {
214
167
  if (ev.target.tagName === 'INPUT') {
215
168
  return;
216
169
  }
217
- // not used currently
218
- // const caseId = get(row, 'case-id.props.data-casenumber');
219
- // navigate to case details page here
220
170
  };
221
- useEffect(() => {
222
- setSelectedCases([]);
223
- }, [props.caseList]);
224
- const onRowSelect = (ev, isSelected, rowindex, rowdata, extradata) => {
225
- if (rowindex === -1) {
226
- isSelected ? setSelectedCases(caseListData.map((kase) => kase.case_number)) : setSelectedCases([]);
227
- }
228
- else {
229
- const caseNumber = get(rowdata, 'cells[0].props.data-casenumber');
230
- setSelectedCases((oldCases) => isSelected ? [...oldCases, caseNumber] : oldCases.filter((caseId) => caseId !== caseNumber));
171
+ const onRowSelect = (ev, caseNumber) => {
172
+ if (!isUndefined(caseNumber)) {
173
+ setSelectedCases((oldCases) => !selectedCases.includes(caseNumber)
174
+ ? [...oldCases, caseNumber]
175
+ : oldCases.filter((caseId) => caseId !== caseNumber));
231
176
  }
232
177
  };
233
178
  // Clear Filters
@@ -251,27 +196,23 @@ export function CaseListTable(props) {
251
196
  return EMPTY_STATE_FILTER_APPLIED;
252
197
  }
253
198
  };
254
- const noResultFoundRow = [
255
- {
256
- heightAuto: true,
257
- cells: [
258
- {
259
- props: { colSpan: 9 },
260
- title: (React.createElement(Bullseye, null,
261
- React.createElement(EmptyState, { variant: EmptyStateVariant.full },
262
- React.createElement(EmptyStateIcon, { icon: SearchIcon }),
263
- React.createElement(Title, { headingLevel: "h2", size: "lg" },
264
- React.createElement(Trans, null, isInternal && (!showingFilter || !hasSearchQuery)
265
- ? 'No results found'
266
- : 'No information to display')),
267
- React.createElement(EmptyStateBody, null,
268
- React.createElement(Trans, null, getEmptyStateErrMessage())),
269
- (showingFilter || hasSearchQuery) && (React.createElement(Button, { variant: "link", onClick: clearAllFilters },
270
- React.createElement(Trans, null, "Clear all")))))),
271
- },
272
- ],
273
- },
274
- ];
199
+ const noResultFoundRow = (React.createElement(Tr, null,
200
+ React.createElement(Td, { colSpan: 8 },
201
+ React.createElement(Bullseye, { style: { minHeight: '350px' } },
202
+ React.createElement(EmptyState, { variant: EmptyStateVariant.full },
203
+ React.createElement(EmptyStateHeader, { titleText: React.createElement(React.Fragment, null,
204
+ React.createElement(Trans, null, isInternal && (!showingFilter || !hasSearchQuery)
205
+ ? 'No results found'
206
+ : 'No information to display')), icon: React.createElement(EmptyStateIcon, { icon: SearchIcon }), headingLevel: "h2" }),
207
+ React.createElement(EmptyStateBody, null,
208
+ React.createElement(Trans, null, getEmptyStateErrMessage())),
209
+ React.createElement(EmptyStateFooter, null, (showingFilter || hasSearchQuery) && (React.createElement(Button, { variant: "link", onClick: clearAllFilters },
210
+ React.createElement(Trans, null, "Clear all")))))))));
211
+ const loadingRowDefault = (React.createElement(Tr, null,
212
+ React.createElement(Td, { colSpan: 8 },
213
+ React.createElement(Bullseye, { style: { minHeight: '350px' } },
214
+ React.createElement(EmptyState, { variant: EmptyStateVariant.sm },
215
+ React.createElement(Spinner, { size: "xl" }))))));
275
216
  const onCasesCloseSuccess = () => {
276
217
  resetFilterToDefaultState(dispatch);
277
218
  };
@@ -289,17 +230,174 @@ export function CaseListTable(props) {
289
230
  onSetPage(paginationInfo);
290
231
  scrollIntoView(tableToolbarRef, { navBarRef, timeout: 0, onlyIfNotInViewport: true, offset: 30 });
291
232
  };
233
+ const getSortableRowValues = (row) => {
234
+ const { case_number, case_summary, case_contactName, case_lastModifiedDate, case_severity, case_status, case_createdDate, case_accountNumber, case_alternate_id, case_type, case_closedDate, case_folderName, case_lastModifiedByName, case_createdByName, case_version, id, case_customer_escalation, case_product, } = row;
235
+ return [
236
+ case_number,
237
+ case_summary,
238
+ case_contactName,
239
+ case_lastModifiedDate,
240
+ case_severity,
241
+ case_status,
242
+ case_createdDate,
243
+ case_accountNumber,
244
+ case_alternate_id,
245
+ case_type,
246
+ case_closedDate,
247
+ case_folderName,
248
+ case_lastModifiedByName,
249
+ case_createdByName,
250
+ case_version,
251
+ id,
252
+ case_customer_escalation,
253
+ case_product,
254
+ ];
255
+ };
256
+ const onSort = (columnIndex) => ({
257
+ sortBy: {
258
+ index: activeSortIndex,
259
+ direction: activeSortDirection,
260
+ },
261
+ onSort: (_event, index, direction) => {
262
+ setActiveSortIndex(index);
263
+ setActiveSortDirection(direction);
264
+ },
265
+ columnIndex,
266
+ });
267
+ const getCaseGroupName = (groupNum) => {
268
+ var _a, _b;
269
+ if (!groupNum || ((_a = props.caseGroups) === null || _a === void 0 ? void 0 : _a.length) < 1)
270
+ return '';
271
+ const group = (_b = props.caseGroups) === null || _b === void 0 ? void 0 : _b.find((group) => group.groupNum === groupNum);
272
+ return (group === null || group === void 0 ? void 0 : group.name) || '';
273
+ };
274
+ const localRows = [
275
+ ...caseListData === null || caseListData === void 0 ? void 0 : caseListData.map((row, index) => ({
276
+ case_number: row.case_number,
277
+ case_summary: row.case_summary,
278
+ case_createdByName: row.case_createdByName,
279
+ case_lastModifiedDate: formatDate(row.case_lastModifiedDate) ? formatDate(row.case_lastModifiedDate) : '',
280
+ case_severity: row.case_severity ? row.case_severity : '',
281
+ case_status: row.case_status,
282
+ case_createdDate: formatDate(row.case_createdDate),
283
+ case_accountNumber: row.case_accountNumber,
284
+ case_alternate_id: row.case_alternate_id ? row.case_alternate_id : '',
285
+ case_type: toNewCaseTypeSwitcher(row.case_type),
286
+ case_closedDate: formatDate(row.case_closedDate) ? formatDate(row.case_closedDate) : '',
287
+ case_folderName: row.case_folderName || getCaseGroupName(row.case_folderNumber) || '',
288
+ case_contactName: row.case_contactName,
289
+ case_lastModifiedByName: row.case_lastModifiedByName ? row.case_lastModifiedByName : '',
290
+ case_version: row.case_version,
291
+ id: row.id,
292
+ case_product: row.case_product,
293
+ case_customer_escalation: row.case_customer_escalation,
294
+ })),
295
+ ];
296
+ useEffect(() => {
297
+ var _a;
298
+ setSelectedCases([]);
299
+ !isEmpty(localRows) ? setSortedCaseListData(localRows) : setSortedCaseListData((_a = props.caseList) === null || _a === void 0 ? void 0 : _a.docs);
300
+ // eslint-disable-next-line react-hooks/exhaustive-deps
301
+ }, [props.caseList]);
302
+ useEffect(() => {
303
+ if (hydraUserPreferences.isFetching)
304
+ return;
305
+ const getSelectedColumnsListFromCache = () => {
306
+ const savedSelectedColumns = find(hydraUserPreferences === null || hydraUserPreferences === void 0 ? void 0 : hydraUserPreferences.data, (pref) => pref.key === UserPreferencesKeys.caseListSelectedColumns);
307
+ if (!isUndefined(savedSelectedColumns) && JSON.parse(savedSelectedColumns === null || savedSelectedColumns === void 0 ? void 0 : savedSelectedColumns.value)) {
308
+ setSelectedColumns(JSON.parse(savedSelectedColumns === null || savedSelectedColumns === void 0 ? void 0 : savedSelectedColumns.value));
309
+ }
310
+ else {
311
+ setSelectedColumns(initialSelectedColumns);
312
+ }
313
+ };
314
+ getSelectedColumnsListFromCache();
315
+ // eslint-disable-next-line react-hooks/exhaustive-deps
316
+ }, []);
317
+ useEffect(() => {
318
+ let sortedRows = localRows;
319
+ if (activeSortIndex !== undefined && activeSortDirection !== undefined) {
320
+ updateSort(dispatch, {
321
+ direction: activeSortDirection,
322
+ column: visibleCaseListColumns[activeSortIndex].id,
323
+ });
324
+ sortedRows = localRows === null || localRows === void 0 ? void 0 : localRows.sort((a, b) => {
325
+ const aValue = getSortableRowValues(a)[activeSortIndex];
326
+ const bValue = getSortableRowValues(b)[activeSortIndex];
327
+ if (typeof aValue === 'number') {
328
+ // Numeric sort
329
+ if (activeSortDirection === 'asc') {
330
+ return aValue - bValue;
331
+ }
332
+ return bValue - aValue;
333
+ }
334
+ else {
335
+ // String sort
336
+ if (activeSortDirection === 'asc') {
337
+ return aValue === null || aValue === void 0 ? void 0 : aValue.localeCompare(bValue);
338
+ }
339
+ return bValue === null || bValue === void 0 ? void 0 : bValue.localeCompare(aValue);
340
+ }
341
+ });
342
+ }
343
+ setSortedCaseListData(sortedRows);
344
+ // eslint-disable-next-line react-hooks/exhaustive-deps
345
+ }, [activeSortDirection, activeSortIndex]);
292
346
  return (React.createElement(React.Fragment, null,
293
- React.createElement(Table, { columns: columns, data: caseListData, selectedColumns: selectedColumns },
294
- React.createElement("div", { className: "case-list-table-toolbar pf-l-flex", ref: tableToolbarRef },
295
- React.createElement("div", { className: "toolbar-actions pf-l-flex pf-m-space-items-sm" },
296
- React.createElement(TableColumnSelector, { onColumnSelectorChange: onColumnSelectorChange }),
297
- React.createElement(ExportCaseListCSV, { currentFilteredCaseList: props.caseList, isExportCsvDisabled: props.isSolrDown }),
347
+ React.createElement(TableComponent, { columns: columns, data: caseListData, selectedColumns: selectedColumns },
348
+ React.createElement("div", { className: "case-list-table-toolbar pf-v5-l-flex", ref: tableToolbarRef },
349
+ React.createElement("div", { className: "toolbar-actions pf-v5-l-flex pf-m-space-items-sm" },
350
+ React.createElement(TableColumnSelector, { onColumnSelectorChange: onColumnSelectorChange, cachedColumns: selectedColumns }),
351
+ React.createElement(ExportCaseListCSV, { currentFilteredCaseList: props.caseList, isExportCsvDisabled: props.isSolrDown, selectedCases: selectedCases }),
298
352
  React.createElement(CloseCaseBtn, { selectedCases: selectedCases, caseList: caseListData, onCasesCloseSuccess: onCasesCloseSuccess })),
299
353
  React.createElement("span", { className: "toolbar-pagination" },
300
354
  React.createElement(TablePagination, { perPage: (_c = props.paginationInfo) === null || _c === void 0 ? void 0 : _c.pageSize, currentPage: (_d = props.paginationInfo) === null || _d === void 0 ? void 0 : _d.currentPage, onPerPageSelect: onPerPageSelect, onSetPage: onSetPage, variant: PaginationVariant.top, itemCount: getItemCount() }))),
301
- React.createElement("div", { className: "pf-c-scroll-inner-wrapper" },
302
- React.createElement(PFTable, { "aria-label": "case-list", className: "case-list-table", pagination: false, onRowClick: onRowClick, onSortChange: onSortChange, onSelect: onRowSelect, emptyStateRow: noResultFoundRow, sortInfo: props.sortInfo, isLoading: props.isCaseListPageLoading })),
303
- caseListData.length > 9 && (React.createElement("footer", { className: "toolbar-pagination" },
304
- React.createElement(TablePagination, { perPage: (_e = props === null || props === void 0 ? void 0 : props.paginationInfo) === null || _e === void 0 ? void 0 : _e.pageSize, currentPage: (_f = props === null || props === void 0 ? void 0 : props.paginationInfo) === null || _f === void 0 ? void 0 : _f.currentPage, onPerPageSelect: onPerPageSelect, onSetPage: onBottomPaginationSetPage, variant: PaginationVariant.bottom, itemCount: getItemCount() }))))));
355
+ React.createElement("div", { className: "pf-v5-c-scroll-inner-wrapper" },
356
+ React.createElement(Table, { variant: TableVariant.compact, "aria-label": "case-list", className: "case-list-table" },
357
+ React.createElement(Thead, null,
358
+ React.createElement(Tr, { key: "tableHeaderRow" },
359
+ React.createElement(Th, { select: {
360
+ onSelect: (_event, isSelecting) => selectAllRows(),
361
+ isSelected: isEqual(selectedCases, allRows),
362
+ }, className: props.isCaseListPageLoading || (caseListData || []).length < 1
363
+ ? Visibility.hidden
364
+ : '', key: "selectAllRowsCheckBox" }),
365
+ visibleCaseListColumns.map((column, index) => (React.createElement(Th, { id: column.id, sort: column.sortable ? onSort(index) : undefined, key: column.id }, column.title))))),
366
+ React.createElement(Tbody, null, !props.isCaseListPageLoading && (caseListData || []).length < 1
367
+ ? noResultFoundRow
368
+ : props.isCaseListPageLoading
369
+ ? loadingRowDefault
370
+ : sortedCaseListData === null || sortedCaseListData === void 0 ? void 0 : sortedCaseListData.map((row, index) => (React.createElement(Tr, { onRowClick: (event) => (onRowClick ? onRowClick(event, row) : ''), key: row === null || row === void 0 ? void 0 : row.case_number },
371
+ React.createElement(Td, { select: {
372
+ rowIndex: index,
373
+ onSelect: (_event, index) => onRowSelect(_event, row === null || row === void 0 ? void 0 : row.case_number),
374
+ isSelected: selectedCases.includes(row === null || row === void 0 ? void 0 : row.case_number),
375
+ } }),
376
+ React.createElement(Th, { dataLabel: "Case ID", id: row.case_number, scope: "row" },
377
+ React.createElement("div", { className: "case-number-section" },
378
+ React.createElement(Link, { to: `/case/${row.case_number}` },
379
+ React.createElement("span", { className: "case-number" }, row.case_number)),
380
+ row.case_customer_escalation ? (React.createElement("div", { className: "escalation-label" },
381
+ React.createElement(Trans, null, "Escalated"))) : (''))),
382
+ React.createElement(Td, { dataLabel: "Title" }, row.case_summary),
383
+ React.createElement(Td, { className: !isColumnVisible('contactName') ? Visibility.hidden : '', dataLabel: "Owner" }, row.case_contactName),
384
+ React.createElement(Td, { className: !isColumnVisible('lastModifiedDate') ? Visibility.hidden : '', dataLabel: "Modified by" },
385
+ React.createElement("span", { className: "modified-name" }, row.case_lastModifiedByName),
386
+ row.case_lastModifiedDate ? formatDate(row.case_lastModifiedDate) : ''),
387
+ React.createElement(Td, { className: !isColumnVisible('severity') ? Visibility.hidden : '', dataLabel: "Severity" },
388
+ React.createElement(SeverityLabel, { sevValue: row.case_severity })),
389
+ React.createElement(Td, { className: !isColumnVisible('status') ? Visibility.hidden : '', dataLabel: "Status" }, row.case_status),
390
+ React.createElement(Td, { className: !isColumnVisible('createdDate') ? Visibility.hidden : '', dataLabel: "Created by" },
391
+ React.createElement("span", { className: "created-name" }, row.case_createdByName),
392
+ row.case_createdDate ? formatDate(row.case_createdDate) : ''),
393
+ React.createElement(Td, { className: !isColumnVisible('product') ? Visibility.hidden : '', dataLabel: "Product and Version" },
394
+ row.case_product,
395
+ React.createElement("span", { style: { display: 'block' } }, row.case_version)),
396
+ React.createElement(Td, { className: !isColumnVisible('accountNumber') ? Visibility.hidden : '', dataLabel: "Account number" }, row.case_accountNumber),
397
+ React.createElement(Td, { className: !isColumnVisible('alternateCaseId') ? Visibility.hidden : '', "data-label": "Personal reference number" }, row.case_alternate_id ? row.case_alternate_id : ''),
398
+ React.createElement(Td, { className: !isColumnVisible('type') ? Visibility.hidden : '', "data-label": "Support type" }, row.case_type),
399
+ React.createElement(Td, { className: !isColumnVisible('closedDate') ? Visibility.hidden : '', "data-label": "Closed date" }, row.case_closedDate ? formatDate(row.case_closedDate) : ''),
400
+ React.createElement(Td, { className: !isColumnVisible('folderName') ? Visibility.hidden : '', "data-label": "Group" }, row.case_folderName ? row.case_folderName : ''))))))),
401
+ React.createElement("footer", { className: "toolbar-pagination", "data-tracking-id": "case-list-table-pagination" },
402
+ React.createElement(TablePagination, { perPage: (_e = props === null || props === void 0 ? void 0 : props.paginationInfo) === null || _e === void 0 ? void 0 : _e.pageSize, currentPage: (_f = props === null || props === void 0 ? void 0 : props.paginationInfo) === null || _f === void 0 ? void 0 : _f.currentPage, onPerPageSelect: onPerPageSelect, onSetPage: onBottomPaginationSetPage, variant: PaginationVariant.bottom, itemCount: getItemCount() })))));
305
403
  }
@@ -1,9 +1,10 @@
1
+ import React from 'react';
1
2
  import { ICaseListResponse } from '../../../models/caseList';
2
3
  interface IProps {
3
4
  selectedCases: string[];
4
5
  caseList: ICaseListResponse[];
5
6
  onCasesCloseSuccess?: () => void;
6
7
  }
7
- export default function CloseCaseBtn({ selectedCases, caseList, onCasesCloseSuccess }: IProps): JSX.Element;
8
+ export default function CloseCaseBtn({ selectedCases, caseList, onCasesCloseSuccess }: IProps): React.JSX.Element;
8
9
  export {};
9
10
  //# sourceMappingURL=CloseCaseBtn.d.ts.map
@@ -1 +1 @@
1
- {"version":3,"file":"CloseCaseBtn.d.ts","sourceRoot":"","sources":["../../../../../src/components/case-list/case-list-table/CloseCaseBtn.tsx"],"names":[],"mappings":"AAOA,OAAO,EAAE,iBAAiB,EAAE,MAAM,0BAA0B,CAAC;AAE7D,UAAU,MAAM;IACZ,aAAa,EAAE,MAAM,EAAE,CAAC;IACxB,QAAQ,EAAE,iBAAiB,EAAE,CAAC;IAC9B,mBAAmB,CAAC,EAAE,MAAM,IAAI,CAAC;CACpC;AAUD,MAAM,CAAC,OAAO,UAAU,YAAY,CAAC,EAAE,aAAa,EAAE,QAAQ,EAAE,mBAAmB,EAAE,EAAE,MAAM,eAiF5F"}
1
+ {"version":3,"file":"CloseCaseBtn.d.ts","sourceRoot":"","sources":["../../../../../src/components/case-list/case-list-table/CloseCaseBtn.tsx"],"names":[],"mappings":"AAKA,OAAO,KAAmB,MAAM,OAAO,CAAC;AAGxC,OAAO,EAAE,iBAAiB,EAAE,MAAM,0BAA0B,CAAC;AAE7D,UAAU,MAAM;IACZ,aAAa,EAAE,MAAM,EAAE,CAAC;IACxB,QAAQ,EAAE,iBAAiB,EAAE,CAAC;IAC9B,mBAAmB,CAAC,EAAE,MAAM,IAAI,CAAC;CACpC;AAUD,MAAM,CAAC,OAAO,UAAU,YAAY,CAAC,EAAE,aAAa,EAAE,QAAQ,EAAE,mBAAmB,EAAE,EAAE,MAAM,qBAsF5F"}
@@ -11,6 +11,7 @@ import { publicApi } from '@cee-eng/hydrajs';
11
11
  import { Button } from '@patternfly/react-core';
12
12
  import { ToastNotification, useFetch } from '@rh-support/components';
13
13
  import { CloseCaseModal, useCanCreateCase } from '@rh-support/react-context';
14
+ import { dtmTrackEventCaseStepEncountered } from '@rh-support/utils';
14
15
  import React, { useState } from 'react';
15
16
  import { Trans, useTranslation } from 'react-i18next';
16
17
  const MAX_ALLOWED_CASES = 5;
@@ -42,7 +43,9 @@ export default function CloseCaseBtn({ selectedCases, caseList, onCasesCloseSucc
42
43
  const promiseArr = [];
43
44
  setIsModalOpen(false);
44
45
  const toastId = ToastNotification.addSuccessMessage(t(`Closing selected cases`));
45
- selectedCases.forEach((caseNumber) => {
46
+ selectedCases.forEach((caseNumber, i) => {
47
+ const product = caseList[i].case_product[0];
48
+ const version = caseList[i].case_version;
46
49
  const p = request(caseNumber, { status: 'Closed' });
47
50
  promiseArr.push(p);
48
51
  p.then((res) => __awaiter(this, void 0, void 0, function* () {
@@ -54,9 +57,11 @@ export default function CloseCaseBtn({ selectedCases, caseList, onCasesCloseSucc
54
57
  });
55
58
  ToastNotification.clearToast(toastId);
56
59
  ToastNotification.addSuccessMessage(t('Case {{caseNumber}} successfully closed', { caseNumber }));
60
+ // Only call dtm track event only when the case has been closed successfully.
61
+ dtmTrackEventCaseStepEncountered('close', caseNumber, product, version);
57
62
  }), (err) => {
58
63
  ToastNotification.clearToast(toastId);
59
- ToastNotification.addDangerMessage('Could not close case {{caseNumber}}', { caseNumber });
64
+ ToastNotification.addDangerMessage(t('Could not close case {{caseNumber}}', { caseNumber }));
60
65
  });
61
66
  });
62
67
  yield Promise.all(promiseArr.map(reflect));
@@ -0,0 +1,19 @@
1
+ import './DownloadCSVFileModal.scss';
2
+ import { IAccount } from '@cee-eng/hydrajs/@types/models/account';
3
+ import { IApiResponseDetails } from '@rh-support/types/shared';
4
+ import { UserAuth } from '@rh-support/user-permissions';
5
+ import React from 'react';
6
+ import { ICaseListFilterState } from '../CaseListFilterReducer';
7
+ interface IProps {
8
+ isDisabled?: boolean;
9
+ onModalshow: boolean;
10
+ onClose: () => void;
11
+ loggedInUserRights: IApiResponseDetails<UserAuth>;
12
+ loggedInUsersAccount: IApiResponseDetails<Partial<IAccount>>;
13
+ filterState: ICaseListFilterState;
14
+ selectedCases: string[];
15
+ filteredCaseCount: number;
16
+ }
17
+ export default function DownloadCSVFileModal(props: IProps): React.JSX.Element;
18
+ export {};
19
+ //# sourceMappingURL=DownloadCSVFileModal.d.ts.map
@@ -0,0 +1 @@
1
+ {"version":3,"file":"DownloadCSVFileModal.d.ts","sourceRoot":"","sources":["../../../../../src/components/case-list/case-list-table/DownloadCSVFileModal.tsx"],"names":[],"mappings":"AAAA,OAAO,6BAA6B,CAAC;AAGrC,OAAO,EAAE,QAAQ,EAAE,MAAM,wCAAwC,CAAC;AAkBlE,OAAO,EAAE,mBAAmB,EAAE,MAAM,0BAA0B,CAAC;AAC/D,OAAO,EAAE,QAAQ,EAAE,MAAM,8BAA8B,CAAC;AAGxD,OAAO,KAAuC,MAAM,OAAO,CAAC;AAM5D,OAAO,EAAE,oBAAoB,EAAE,MAAM,0BAA0B,CAAC;AAEhE,UAAU,MAAM;IACZ,UAAU,CAAC,EAAE,OAAO,CAAC;IACrB,WAAW,EAAE,OAAO,CAAC;IACrB,OAAO,EAAE,MAAM,IAAI,CAAC;IACpB,kBAAkB,EAAE,mBAAmB,CAAC,QAAQ,CAAC,CAAC;IAClD,oBAAoB,EAAE,mBAAmB,CAAC,OAAO,CAAC,QAAQ,CAAC,CAAC,CAAC;IAC7D,WAAW,EAAE,oBAAoB,CAAC;IAClC,aAAa,EAAE,MAAM,EAAE,CAAC;IACxB,iBAAiB,EAAE,MAAM,CAAC;CAC7B;AAoBD,MAAM,CAAC,OAAO,UAAU,oBAAoB,CAAC,KAAK,EAAE,MAAM,qBAgazD"}