@openshift-assisted/ui-lib 2.39.5 → 2.41.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 (156) hide show
  1. package/build/@types/cim/components/InfraEnv/InfraTableToolbar.d.ts.map +1 -1
  2. package/build/@types/cim/components/helpers/toAssisted.d.ts.map +1 -1
  3. package/build/@types/cim/index.d.ts +1 -0
  4. package/build/@types/cim/index.d.ts.map +1 -1
  5. package/build/@types/common/api/assisted-service/ClustersAPI.d.ts +1 -0
  6. package/build/@types/common/api/assisted-service/ClustersAPI.d.ts.map +1 -1
  7. package/build/@types/common/components/clusterDetail/ClusterCredentials.d.ts.map +1 -1
  8. package/build/@types/common/components/clusterWizard/ClusterWizardStep.d.ts.map +1 -1
  9. package/build/@types/common/components/operators/operatorSpecs.d.ts.map +1 -1
  10. package/build/@types/common/components/ui/ClusterEventsToolbar.d.ts.map +1 -1
  11. package/build/@types/common/components/ui/WizardFooter.d.ts +1 -0
  12. package/build/@types/common/components/ui/WizardFooter.d.ts.map +1 -1
  13. package/build/@types/common/components/ui/WizardNavItem.d.ts +1 -1
  14. package/build/@types/common/components/ui/WizardNavItem.d.ts.map +1 -1
  15. package/build/@types/common/components/ui/formik/MultiSelectField.d.ts.map +1 -1
  16. package/build/@types/common/components/ui/formik/types.d.ts +2 -2
  17. package/build/@types/common/components/ui/formik/types.d.ts.map +1 -1
  18. package/build/@types/common/components/ui/utils.d.ts +1 -1
  19. package/build/@types/common/components/ui/utils.d.ts.map +1 -1
  20. package/build/@types/common/config/constants.d.ts.map +1 -1
  21. package/build/@types/common/config/docs_links.d.ts +1 -0
  22. package/build/@types/common/config/docs_links.d.ts.map +1 -1
  23. package/build/@types/common/index.d.ts +0 -3
  24. package/build/@types/common/index.d.ts.map +1 -1
  25. package/build/@types/ocm/components/HostsClusterDetailTab/utils.d.ts.map +1 -1
  26. package/build/@types/ocm/components/clusterConfiguration/CustomManifestCheckbox.d.ts.map +1 -1
  27. package/build/@types/ocm/components/clusterConfiguration/networkConfiguration/NetworkConfigurationForm.d.ts.map +1 -1
  28. package/build/@types/ocm/components/clusterConfiguration/operators/bundleSpecs.d.ts.map +1 -1
  29. package/build/@types/ocm/components/clusterConfiguration/staticIp/components/StaticIpPage.d.ts.map +1 -1
  30. package/build/@types/ocm/components/clusterDetail/ClusterDetailStatusMessages.d.ts.map +1 -1
  31. package/build/@types/ocm/components/clusterDetail/ClusterDetailsButtonGroup.d.ts +1 -0
  32. package/build/@types/ocm/components/clusterDetail/ClusterDetailsButtonGroup.d.ts.map +1 -1
  33. package/build/@types/ocm/components/clusterWizard/ClusterDetails.d.ts.map +1 -1
  34. package/build/@types/ocm/components/clusterWizard/CredentialsDownload.d.ts +7 -0
  35. package/build/@types/ocm/components/clusterWizard/CredentialsDownload.d.ts.map +1 -0
  36. package/build/@types/ocm/components/clusterWizard/wizardTransition.d.ts +1 -1
  37. package/build/@types/ocm/components/clusterWizard/wizardTransition.d.ts.map +1 -1
  38. package/build/@types/ocm/components/clusters/ClustersListToolbar.d.ts.map +1 -1
  39. package/build/@types/ocm/config/constants.d.ts +0 -2
  40. package/build/@types/ocm/config/constants.d.ts.map +1 -1
  41. package/build/@types/ocm/services/ClustersService.d.ts +0 -1
  42. package/build/@types/ocm/services/ClustersService.d.ts.map +1 -1
  43. package/build/cjs/cim/components/ClusterDeployment/ShortCapacitySummary.js +1 -1
  44. package/build/cjs/cim/components/ClusterDeployment/ShortCapacitySummary.js.map +1 -1
  45. package/build/cjs/cim/components/InfraEnv/InfraTableToolbar.js +12 -12
  46. package/build/cjs/cim/components/InfraEnv/InfraTableToolbar.js.map +1 -1
  47. package/build/cjs/cim/components/helpers/toAssisted.js +3 -5
  48. package/build/cjs/cim/components/helpers/toAssisted.js.map +1 -1
  49. package/build/cjs/cim/components/helpers/versions.js +1 -1
  50. package/build/cjs/cim/components/helpers/versions.js.map +1 -1
  51. package/build/cjs/cim/index.js +1 -0
  52. package/build/cjs/cim/index.js.map +1 -1
  53. package/build/cjs/common/api/assisted-service/ClustersAPI.js +5 -0
  54. package/build/cjs/common/api/assisted-service/ClustersAPI.js.map +1 -1
  55. package/build/cjs/common/components/clusterDetail/ClusterCredentials.js +1 -1
  56. package/build/cjs/common/components/clusterDetail/ClusterCredentials.js.map +1 -1
  57. package/build/cjs/common/components/clusterWizard/ClusterWizardStep.js +2 -4
  58. package/build/cjs/common/components/clusterWizard/ClusterWizardStep.js.map +1 -1
  59. package/build/cjs/common/components/operators/operatorSpecs.js +2 -2
  60. package/build/cjs/common/components/operators/operatorSpecs.js.map +1 -1
  61. package/build/cjs/common/components/ui/ClusterEventsToolbar.js +18 -10
  62. package/build/cjs/common/components/ui/ClusterEventsToolbar.js.map +1 -1
  63. package/build/cjs/common/components/ui/WizardFooter.js +2 -2
  64. package/build/cjs/common/components/ui/WizardFooter.js.map +1 -1
  65. package/build/cjs/common/components/ui/WizardNavItem.js +2 -2
  66. package/build/cjs/common/components/ui/WizardNavItem.js.map +1 -1
  67. package/build/cjs/common/components/ui/formik/MultiSelectField.js +26 -28
  68. package/build/cjs/common/components/ui/formik/MultiSelectField.js.map +1 -1
  69. package/build/cjs/common/components/ui/utils.js +1 -1
  70. package/build/cjs/common/components/ui/utils.js.map +1 -1
  71. package/build/cjs/common/config/constants.js +4 -6
  72. package/build/cjs/common/config/constants.js.map +1 -1
  73. package/build/cjs/common/config/docs_links.js +2 -1
  74. package/build/cjs/common/config/docs_links.js.map +1 -1
  75. package/build/cjs/common/index.js +0 -3
  76. package/build/cjs/common/index.js.map +1 -1
  77. package/build/cjs/ocm/components/AddHosts/day2Wizard/Day2Wizard.js +2 -2
  78. package/build/cjs/ocm/components/AddHosts/day2Wizard/Day2Wizard.js.map +1 -1
  79. package/build/cjs/ocm/components/AddHosts/day2Wizard/Day2WizardNav.js +5 -5
  80. package/build/cjs/ocm/components/AddHosts/day2Wizard/Day2WizardNav.js.map +1 -1
  81. package/build/cjs/ocm/components/HostsClusterDetailTab/utils.js +8 -4
  82. package/build/cjs/ocm/components/HostsClusterDetailTab/utils.js.map +1 -1
  83. package/build/cjs/ocm/components/clusterConfiguration/CustomManifestCheckbox.js +0 -11
  84. package/build/cjs/ocm/components/clusterConfiguration/CustomManifestCheckbox.js.map +1 -1
  85. package/build/cjs/ocm/components/clusterConfiguration/networkConfiguration/NetworkConfigurationForm.js +23 -1
  86. package/build/cjs/ocm/components/clusterConfiguration/networkConfiguration/NetworkConfigurationForm.js.map +1 -1
  87. package/build/cjs/ocm/components/clusterConfiguration/operators/OperatorCheckbox.js +2 -2
  88. package/build/cjs/ocm/components/clusterConfiguration/operators/bundleSpecs.js +6 -20
  89. package/build/cjs/ocm/components/clusterConfiguration/operators/bundleSpecs.js.map +1 -1
  90. package/build/cjs/ocm/components/clusterConfiguration/staticIp/components/StaticIpPage.js +3 -3
  91. package/build/cjs/ocm/components/clusterConfiguration/staticIp/components/StaticIpPage.js.map +1 -1
  92. package/build/cjs/ocm/components/clusterDetail/ClusterDetailStatusMessages.js +16 -14
  93. package/build/cjs/ocm/components/clusterDetail/ClusterDetailStatusMessages.js.map +1 -1
  94. package/build/cjs/ocm/components/clusterDetail/ClusterDetailsButtonGroup.js +1 -0
  95. package/build/cjs/ocm/components/clusterDetail/ClusterDetailsButtonGroup.js.map +1 -1
  96. package/build/cjs/ocm/components/clusterWizard/ClusterDetails.js +6 -2
  97. package/build/cjs/ocm/components/clusterWizard/ClusterDetails.js.map +1 -1
  98. package/build/cjs/ocm/components/clusterWizard/ClusterWizard.js +3 -3
  99. package/build/cjs/ocm/components/clusterWizard/ClusterWizard.js.map +1 -1
  100. package/build/cjs/ocm/components/clusterWizard/ClusterWizardContextProvider.js +1 -1
  101. package/build/cjs/ocm/components/clusterWizard/ClusterWizardContextProvider.js.map +1 -1
  102. package/build/cjs/ocm/components/clusterWizard/ClusterWizardNavigation.js +5 -5
  103. package/build/cjs/ocm/components/clusterWizard/ClusterWizardNavigation.js.map +1 -1
  104. package/build/cjs/ocm/components/clusterWizard/CredentialsDownload.js +62 -0
  105. package/build/cjs/ocm/components/clusterWizard/CredentialsDownload.js.map +1 -0
  106. package/build/cjs/ocm/components/clusterWizard/constants.js +1 -1
  107. package/build/cjs/ocm/components/clusterWizard/constants.js.map +1 -1
  108. package/build/cjs/ocm/components/clusterWizard/wizardTransition.js +3 -3
  109. package/build/cjs/ocm/components/clusterWizard/wizardTransition.js.map +1 -1
  110. package/build/cjs/ocm/components/clusters/ClustersListToolbar.js +3 -3
  111. package/build/cjs/ocm/components/clusters/ClustersListToolbar.js.map +1 -1
  112. package/build/cjs/ocm/config/constants.js +1 -155
  113. package/build/cjs/ocm/config/constants.js.map +1 -1
  114. package/build/cjs/ocm/services/ClustersService.js +0 -26
  115. package/build/cjs/ocm/services/ClustersService.js.map +1 -1
  116. package/lib/cim/components/ClusterDeployment/ShortCapacitySummary.tsx +1 -1
  117. package/lib/cim/components/InfraEnv/InfraTableToolbar.tsx +40 -28
  118. package/lib/cim/components/helpers/toAssisted.ts +3 -4
  119. package/lib/cim/components/helpers/versions.ts +1 -1
  120. package/lib/cim/index.ts +1 -0
  121. package/lib/common/api/assisted-service/ClustersAPI.ts +6 -0
  122. package/lib/common/components/clusterDetail/ClusterCredentials.tsx +12 -2
  123. package/lib/common/components/clusterWizard/ClusterWizardStep.tsx +2 -4
  124. package/lib/common/components/operators/operatorSpecs.tsx +3 -2
  125. package/lib/common/components/ui/ClusterEventsToolbar.tsx +78 -45
  126. package/lib/common/components/ui/WizardFooter.tsx +3 -0
  127. package/lib/common/components/ui/WizardNavItem.tsx +1 -1
  128. package/lib/common/components/ui/formik/MultiSelectField.tsx +98 -58
  129. package/lib/common/components/ui/formik/types.ts +2 -2
  130. package/lib/common/components/ui/utils.ts +4 -2
  131. package/lib/common/config/constants.ts +4 -6
  132. package/lib/common/config/docs_links.ts +3 -0
  133. package/lib/common/index.ts +0 -4
  134. package/lib/ocm/components/AddHosts/day2Wizard/Day2Wizard.tsx +1 -1
  135. package/lib/ocm/components/AddHosts/day2Wizard/Day2WizardNav.tsx +5 -5
  136. package/lib/ocm/components/HostsClusterDetailTab/utils.ts +5 -1
  137. package/lib/ocm/components/clusterConfiguration/CustomManifestCheckbox.tsx +0 -13
  138. package/lib/ocm/components/clusterConfiguration/networkConfiguration/NetworkConfigurationForm.tsx +29 -1
  139. package/lib/ocm/components/clusterConfiguration/operators/OperatorCheckbox.tsx +2 -2
  140. package/lib/ocm/components/clusterConfiguration/operators/bundleSpecs.tsx +8 -26
  141. package/lib/ocm/components/clusterConfiguration/staticIp/components/StaticIpPage.tsx +9 -7
  142. package/lib/ocm/components/clusterDetail/ClusterDetailStatusMessages.tsx +18 -19
  143. package/lib/ocm/components/clusterDetail/ClusterDetailsButtonGroup.tsx +2 -0
  144. package/lib/ocm/components/clusterWizard/ClusterDetails.tsx +6 -2
  145. package/lib/ocm/components/clusterWizard/ClusterWizard.tsx +3 -3
  146. package/lib/ocm/components/clusterWizard/ClusterWizardContextProvider.tsx +1 -1
  147. package/lib/ocm/components/clusterWizard/ClusterWizardNavigation.tsx +5 -5
  148. package/lib/ocm/components/clusterWizard/CredentialsDownload.tsx +105 -0
  149. package/lib/ocm/components/clusterWizard/constants.ts +1 -1
  150. package/lib/ocm/components/clusterWizard/wizardTransition.ts +4 -4
  151. package/lib/ocm/components/clusters/ClustersListToolbar.tsx +39 -19
  152. package/lib/ocm/config/constants.ts +0 -156
  153. package/lib/ocm/services/ClustersService.ts +0 -29
  154. package/package.json +3 -3
  155. /package/build/cjs/{common/styles.css → ocm/components/clusterDetail/ClusterDetailsButtonGroup.css} +0 -0
  156. /package/lib/{common/styles.css → ocm/components/clusterDetail/ClusterDetailsButtonGroup.css} +0 -0
@@ -1,5 +1,12 @@
1
1
  import React from 'react';
2
- import { GridItem, ClipboardCopy, clipboardCopyFunc, Button, Alert } from '@patternfly/react-core';
2
+ import {
3
+ GridItem,
4
+ ClipboardCopy,
5
+ clipboardCopyFunc,
6
+ Button,
7
+ Alert,
8
+ TextInput,
9
+ } from '@patternfly/react-core';
3
10
  import { Credentials, Cluster } from '@openshift-assisted/types/assisted-installer-service';
4
11
  import { LoadingState, ErrorState } from '../../components/ui/uiState';
5
12
  import { DetailList, DetailItem } from '../../components/ui/DetailList';
@@ -98,7 +105,10 @@ const ClusterCredentials: React.FC<ClusterCredentialsProps> = ({
98
105
  )}
99
106
  {credentials.username && (
100
107
  <>
101
- <DetailItem title="Username" value={credentials.username} />
108
+ <DetailItem
109
+ title={t('ai:Username')}
110
+ value={<TextInput value={credentials.username} readOnlyVariant="default" />}
111
+ />
102
112
  <DetailItem
103
113
  title={t('ai:Password')}
104
114
  value={
@@ -1,5 +1,5 @@
1
1
  import React from 'react';
2
- import { WizardBody, WizardBodyProps } from '@patternfly/react-core/deprecated';
2
+ import { WizardBody } from '@patternfly/react-core';
3
3
  import { css } from '@patternfly/react-styles';
4
4
 
5
5
  import './ClusterWizardStep.css';
@@ -14,13 +14,11 @@ export const ClusterWizardStep = ({
14
14
  footer,
15
15
  children,
16
16
  }: React.PropsWithChildren<ClusterWizardStepProps>) => {
17
- // activeStep is required, but we're not passing it. Using the cast to avoid TS error
18
- const activeStep = undefined as unknown as WizardBodyProps['activeStep'];
19
17
  return (
20
18
  <div className={css('pf-v5-c-wizard__outer-wrap', 'cluster-wizard-step')}>
21
19
  <div className={css('pf-v5-c-wizard__inner-wrap')}>
22
20
  {navigation}
23
- <WizardBody aria-labelledby="step-id" hasNoBodyPadding={false} activeStep={activeStep}>
21
+ <WizardBody aria-labelledby="step-id" hasNoPadding={false}>
24
22
  {children}
25
23
  </WizardBody>
26
24
  </div>
@@ -30,6 +30,7 @@ import {
30
30
  AUTHORINO_OPERATOR_LINK,
31
31
  CNV_LINK,
32
32
  FENCE_AGENTS_REMEDIATION_LINK,
33
+ getKubeDeschedulerLink,
33
34
  getLsoLink,
34
35
  getLvmsDocsLink,
35
36
  getMceDocsLink,
@@ -154,10 +155,10 @@ export const getOperatorSpecs = (useLVMS?: boolean): { [key: string]: OperatorSp
154
155
  [OPERATOR_NAME_KUBE_DESCHEDULER]: {
155
156
  title: 'Kube Descheduler',
156
157
  featureId: 'KUBE_DESCHEDULER',
157
- Description: () => (
158
+ Description: ({ openshiftVersion }) => (
158
159
  <>
159
160
  Evicts pods to reschedule them onto more suitable nodes.{' '}
160
- <ExternalLink href={NODE_HEALTHCHECK_LINK}>Learn more</ExternalLink>
161
+ <ExternalLink href={getKubeDeschedulerLink(openshiftVersion)}>Learn more</ExternalLink>
161
162
  </>
162
163
  ),
163
164
  notStandalone: true,
@@ -16,8 +16,12 @@ import {
16
16
  Badge,
17
17
  TextInputTypes,
18
18
  InputGroupItem,
19
+ Dropdown,
20
+ DropdownItem,
21
+ DropdownList,
22
+ MenuToggle,
23
+ MenuToggleElement,
19
24
  } from '@patternfly/react-core';
20
- import { Select, SelectOption, SelectProps } from '@patternfly/react-core/deprecated';
21
25
  import { SearchIcon } from '@patternfly/react-icons/dist/js/icons/search-icon';
22
26
  import { FilterIcon } from '@patternfly/react-icons/dist/js/icons/filter-icon';
23
27
  import type { ClusterEventsFiltersType } from '../../types';
@@ -137,7 +141,7 @@ const ClusterEventsToolbar = ({
137
141
  setFilters(nextFilters);
138
142
  };
139
143
 
140
- const onHostToggle: SelectProps['onToggle'] = () => setHostExpanded(!isHostExpanded);
144
+ const onHostToggle = () => setHostExpanded(!isHostExpanded);
141
145
  const onHostSelect = (value: string, isChecked: boolean) => {
142
146
  switch (value) {
143
147
  case DELETED_HOSTS:
@@ -157,7 +161,7 @@ const ClusterEventsToolbar = ({
157
161
  }
158
162
  };
159
163
 
160
- const onSeverityToggle: SelectProps['onToggle'] = () => setSeverityExpanded(!isSeverityExpanded);
164
+ const onSeverityToggle = () => setSeverityExpanded(!isSeverityExpanded);
161
165
  const onSeveritySelect = (value: string, isChecked: boolean) => {
162
166
  onSelect('severities', isChecked, value);
163
167
  };
@@ -227,41 +231,56 @@ const ClusterEventsToolbar = ({
227
231
  }
228
232
  deleteChipGroup={onDeleteChipGroup}
229
233
  >
230
- <Select
231
- variant="checkbox"
232
- aria-label="hosts"
233
- toggleId="cluster-events-hosts-dropdown-button"
234
- onToggle={onHostToggle}
235
- onSelect={(e, value) => onHostSelect(value as string, isSelectEventChecked(e))}
236
- selections={getSelections()}
237
- customBadgeText={hostChips.length}
234
+ <Dropdown
238
235
  isOpen={isHostExpanded}
239
- placeholderText={<Placeholder text="Hosts" />}
240
- maxHeight={280}
241
- zIndex={600}
236
+ onSelect={(e, value) => onHostSelect(value as string, isSelectEventChecked(e))}
237
+ onOpenChange={onHostToggle}
238
+ toggle={(toggleRef: React.Ref<MenuToggleElement>) => (
239
+ <MenuToggle
240
+ id="cluster-events-hosts-dropdown-button"
241
+ ref={toggleRef}
242
+ isFullWidth
243
+ onClick={onHostToggle}
244
+ isExpanded={isHostExpanded}
245
+ badge={hostChips.length && <Badge isRead>{hostChips.length}</Badge>}
246
+ >
247
+ <Placeholder text="Hosts" />
248
+ </MenuToggle>
249
+ )}
250
+ shouldFocusToggleOnSelect
242
251
  >
243
- {[
244
- <SelectOption
245
- inputId={`checkbox-${CLUSTER_LEVEL}`}
252
+ <DropdownList>
253
+ <DropdownItem
254
+ id={`checkbox-${CLUSTER_LEVEL}`}
255
+ hasCheckbox
256
+ isSelected={getSelections().includes(CLUSTER_LEVEL)}
246
257
  key={CLUSTER_LEVEL}
247
258
  value={CLUSTER_LEVEL}
248
259
  >
249
260
  {t('ai:Cluster-level events')}
250
- </SelectOption>,
251
- <SelectOption
252
- inputId={`checkbox-${DELETED_HOSTS}`}
261
+ </DropdownItem>
262
+ <DropdownItem
263
+ id={`checkbox-${DELETED_HOSTS}`}
264
+ hasCheckbox
265
+ isSelected={getSelections().includes(DELETED_HOSTS)}
253
266
  key={DELETED_HOSTS}
254
267
  value={DELETED_HOSTS}
255
268
  >
256
269
  {t('ai:Deleted hosts')}
257
- </SelectOption>,
258
- ...sortedHosts.map((host) => (
259
- <SelectOption inputId={`checkbox-${host.id}`} key={host.id} value={host.id}>
270
+ </DropdownItem>
271
+ {...sortedHosts.map((host) => (
272
+ <DropdownItem
273
+ id={`checkbox-${host.id}`}
274
+ hasCheckbox
275
+ isSelected={getSelections().includes(host.id)}
276
+ key={host.id}
277
+ value={host.id}
278
+ >
260
279
  {host.hostname}
261
- </SelectOption>
262
- )),
263
- ]}
264
- </Select>
280
+ </DropdownItem>
281
+ ))}
282
+ </DropdownList>
283
+ </Dropdown>
265
284
  </CustomToolbarFilter>
266
285
  )}
267
286
 
@@ -278,28 +297,42 @@ const ClusterEventsToolbar = ({
278
297
  deleteChipGroup={onDeleteChipGroup}
279
298
  categoryName="Severity"
280
299
  >
281
- <Select
282
- variant="checkbox"
283
- aria-label="Severity"
284
- toggleId="cluster-events-severity-dropdown-button"
285
- onToggle={onSeverityToggle}
300
+ <Dropdown
301
+ isOpen={isSeverityExpanded}
286
302
  onSelect={(event, value) =>
287
303
  onSeveritySelect(value as string, isSelectEventChecked(event))
288
304
  }
289
- selections={filters.severities}
290
- isOpen={isSeverityExpanded}
291
- placeholderText={<Placeholder text="Severity" />}
292
- >
293
- {EVENT_SEVERITIES.map((severity) => (
294
- <SelectOption
295
- data-testid={`${severity}-filter-option`}
296
- key={severity}
297
- value={severity}
305
+ onOpenChange={onSeverityToggle}
306
+ toggle={(toggleRef: React.Ref<MenuToggleElement>) => (
307
+ <MenuToggle
308
+ id="cluster-events-severity-dropdown-button"
309
+ ref={toggleRef}
310
+ isFullWidth
311
+ onClick={onSeverityToggle}
312
+ isExpanded={isSeverityExpanded}
313
+ badge={
314
+ filters.severities?.length && <Badge isRead>{filters.severities.length}</Badge>
315
+ }
298
316
  >
299
- {capitalize(severity)} <Badge isRead>{severityCounts[severity]}</Badge>
300
- </SelectOption>
301
- ))}
302
- </Select>
317
+ <Placeholder text="Severity" />
318
+ </MenuToggle>
319
+ )}
320
+ shouldFocusToggleOnSelect
321
+ >
322
+ <DropdownList>
323
+ {EVENT_SEVERITIES.map((severity) => (
324
+ <DropdownItem
325
+ data-testid={`${severity}-filter-option`}
326
+ hasCheckbox
327
+ isSelected={filters.severities?.includes(severity)}
328
+ key={severity}
329
+ value={severity}
330
+ >
331
+ {capitalize(severity)} <Badge isRead>{severityCounts[severity]}</Badge>
332
+ </DropdownItem>
333
+ ))}
334
+ </DropdownList>
335
+ </Dropdown>
303
336
  </ToolbarFilter>
304
337
 
305
338
  <ToolbarItem>
@@ -26,6 +26,7 @@ export type WizardFooterGenericProps = {
26
26
  isSubmitting?: boolean;
27
27
  submittingText?: string;
28
28
  nextButtonText?: string;
29
+ isNextButtonLoading?: boolean;
29
30
  };
30
31
 
31
32
  type WizardFooterProps = WizardFooterGenericProps & {
@@ -51,6 +52,7 @@ export const WizardFooter: React.FC<WizardFooterProps> = ({
51
52
  nextButtonText,
52
53
  cluster,
53
54
  onFetchEvents,
55
+ isNextButtonLoading,
54
56
  }) => {
55
57
  const { t } = useTranslation();
56
58
  submittingText = submittingText || t('ai:Saving changes...');
@@ -68,6 +70,7 @@ export const WizardFooter: React.FC<WizardFooterProps> = ({
68
70
  name="next"
69
71
  onClick={onNext}
70
72
  isDisabled={isNextDisabled}
73
+ isLoading={isNextButtonLoading}
71
74
  >
72
75
  {nextButtonText || t('ai:Next')}
73
76
  </Button>
@@ -1,5 +1,5 @@
1
1
  import React, { PropsWithChildren, ReactNode } from 'react';
2
- import { WizardNavItem, WizardNavItemProps } from '@patternfly/react-core/deprecated';
2
+ import { WizardNavItem, WizardNavItemProps } from '@patternfly/react-core';
3
3
  import { ExclamationCircleIcon } from '@patternfly/react-icons/dist/js/icons/exclamation-circle-icon';
4
4
  import UiIcon from './UiIcon';
5
5
 
@@ -1,19 +1,27 @@
1
1
  import React from 'react';
2
2
  import { useField } from 'formik';
3
- import Fuse from 'fuse.js';
4
- import { FormGroup, FormHelperText, HelperText, HelperTextItem } from '@patternfly/react-core';
5
3
  import {
6
- Select,
7
- SelectOption,
8
- SelectOptionObject,
9
- SelectOptionProps,
10
- SelectProps,
11
- SelectVariant,
12
- } from '@patternfly/react-core/deprecated';
13
- import { MultiSelectFieldProps, MultiSelectOption } from './types';
4
+ FormGroup,
5
+ FormHelperText,
6
+ HelperText,
7
+ HelperTextItem,
8
+ Dropdown,
9
+ DropdownItem,
10
+ DropdownList,
11
+ MenuToggle,
12
+ MenuToggleElement,
13
+ TextInputGroup,
14
+ TextInputGroupMain,
15
+ TextInputGroupUtilities,
16
+ Button,
17
+ LabelGroup,
18
+ Label,
19
+ } from '@patternfly/react-core';
20
+ import { MultiSelectFieldProps } from './types';
14
21
  import { getFieldId } from './utils';
15
- import { useTranslation } from '../../../hooks/use-translation-wrapper';
16
22
  import ExclamationCircleIcon from '@patternfly/react-icons/dist/js/icons/exclamation-circle-icon';
23
+ import TimesIcon from '@patternfly/react-icons/dist/js/icons/times-icon';
24
+ import { useTranslation } from '../../../hooks/use-translation-wrapper';
17
25
 
18
26
  // Field value is a string[]
19
27
  const MultiSelectField: React.FC<MultiSelectFieldProps> = ({
@@ -29,21 +37,24 @@ const MultiSelectField: React.FC<MultiSelectFieldProps> = ({
29
37
  ...props
30
38
  }) => {
31
39
  const [isOpen, setOpen] = React.useState(false);
40
+ const [textValue, setTextValue] = React.useState('');
32
41
  const [field, { touched, error }, { setValue }] = useField<string[]>(props.name);
33
42
  const fieldId = getFieldId(props.name, 'multiinput', idPostfix);
34
43
  const isValid = !(touched && error);
35
44
  const errorMessage = !isValid ? error : '';
36
45
  const hText = getHelperText ? getHelperText(field.value?.join(',') || '') : helperText;
46
+ const { t } = useTranslation();
37
47
 
38
48
  const onToggle = (isOpen: boolean) => setOpen(isOpen);
39
49
  const onClearSelection = () => {
40
50
  // onChange && onChange(event);
41
51
  setValue([]);
52
+ setTextValue('');
42
53
  onChange && onChange([]);
43
54
  setOpen(false);
44
55
  };
45
56
 
46
- const onSelect: SelectProps['onSelect'] = (event, selection) => {
57
+ const onSelect = (selection: string) => {
47
58
  // already selected
48
59
  const selected = field.value;
49
60
 
@@ -53,7 +64,7 @@ const MultiSelectField: React.FC<MultiSelectFieldProps> = ({
53
64
  selection as {
54
65
  /* TypeScript hack, debug hint: created as part of "selections" array below */ value?: string;
55
66
  }
56
- ).value || (selection as string);
67
+ ).value || selection;
57
68
 
58
69
  let newValue: string[];
59
70
  if (selected.includes(selectionValue)) {
@@ -65,61 +76,90 @@ const MultiSelectField: React.FC<MultiSelectFieldProps> = ({
65
76
  onChange && onChange(newValue);
66
77
  };
67
78
 
68
- // list of already selected options
69
- const selections: (SelectOptionObject | string)[] = field.value.map((value: string) => {
70
- const option = options.find((opt) => opt.value === value);
71
- return option
72
- ? {
73
- value: option.value,
74
- toString: () => option.displayName,
75
- compareTo: (selectOption: { value: string }) => selectOption.value === value,
76
- }
77
- : value;
79
+ const deleteChip = (chip: string) => {
80
+ const newValue = field.value.filter((val) => val !== chip);
81
+ setValue(newValue);
82
+ setTextValue('');
83
+ onChange && onChange(newValue);
84
+ };
85
+
86
+ const filteredOptions = options.filter((option) => {
87
+ const value = option.value as string;
88
+ return (
89
+ option.displayName.toLowerCase().includes(textValue.toLowerCase()) &&
90
+ !(field.value || []).includes(value.toString())
91
+ );
78
92
  });
79
93
 
80
- const children = options
81
- .filter((option) => !(field.value || []).includes(option.value.toString()))
82
- .map((option) => (
83
- <SelectOption key={option.id} id={option.id} value={option.value}>
94
+ const children = filteredOptions.map((option) => {
95
+ const value = option.value as string;
96
+ return (
97
+ <DropdownItem key={option.id} id={option.id} value={value}>
84
98
  {option.displayName}
85
- </SelectOption>
86
- ));
87
-
88
- const fuse = new Fuse(options, {
89
- ignoreLocation: true,
90
- keys: ['displayName'],
99
+ </DropdownItem>
100
+ );
91
101
  });
92
- const { t } = useTranslation();
93
102
 
94
103
  return (
95
104
  <FormGroup fieldId={fieldId} label={label} isRequired={isRequired} labelIcon={labelIcon}>
96
- <Select
97
- {...field}
98
- {...props}
105
+ <Dropdown
99
106
  id={fieldId}
100
- variant={SelectVariant.typeaheadMulti}
101
- typeAheadAriaLabel={t('ai:Select a state')}
102
- validated={isValid ? 'default' : 'error'}
103
- aria-describedby={`${fieldId}-helper`}
104
- isCreatable={false}
105
- placeholderText={placeholderText}
106
107
  isOpen={isOpen}
107
- onToggle={(_event, isOpen: boolean) => onToggle(isOpen)}
108
- onSelect={onSelect}
109
- onClear={onClearSelection}
110
- selections={selections}
111
- onFilter={(e, val) => {
112
- if (!val || val === '') {
113
- return children;
114
- }
115
- const results = fuse.search<MultiSelectOption>(val).map((result) => result.item.id);
116
- return (
117
- React.Children.toArray(children) as React.ReactElement<SelectOptionProps>[]
118
- ).filter(({ props }) => results.includes(props.id as string));
119
- }}
108
+ onSelect={(event, value) => onSelect(value as string)}
109
+ onOpenChange={onToggle}
110
+ toggle={(toggleRef: React.Ref<MenuToggleElement>) => (
111
+ <MenuToggle
112
+ ref={toggleRef}
113
+ isFullWidth
114
+ onClick={() => onToggle(!isOpen)}
115
+ isExpanded={isOpen}
116
+ variant="typeahead"
117
+ >
118
+ <TextInputGroup>
119
+ <LabelGroup>
120
+ {field.value.map((currentChip) => (
121
+ <Label
122
+ key={currentChip}
123
+ variant="outline"
124
+ onClose={() => deleteChip(currentChip)}
125
+ >
126
+ {currentChip}
127
+ </Label>
128
+ ))}
129
+ </LabelGroup>
130
+ <TextInputGroupMain
131
+ placeholder={placeholderText}
132
+ onClick={() => onToggle(!isOpen)}
133
+ value={textValue}
134
+ onChange={(event, value) => setTextValue(value)}
135
+ />
136
+ <TextInputGroupUtilities>
137
+ <Button
138
+ variant="plain"
139
+ onClick={onClearSelection}
140
+ aria-label="Clear button and input"
141
+ icon={<TimesIcon />}
142
+ />
143
+ </TextInputGroupUtilities>
144
+ </TextInputGroup>
145
+ </MenuToggle>
146
+ )}
147
+ shouldFocusToggleOnSelect
120
148
  >
121
- {children}
122
- </Select>
149
+ <DropdownList>
150
+ {children.length ? (
151
+ children
152
+ ) : (
153
+ <DropdownItem
154
+ key="No options available"
155
+ id="No options available"
156
+ value="No options available"
157
+ >
158
+ {t('ai:No options available')}
159
+ </DropdownItem>
160
+ )}
161
+ </DropdownList>
162
+ </Dropdown>
123
163
  {(errorMessage || hText) && (
124
164
  <FormHelperText>
125
165
  <HelperText>
@@ -7,7 +7,7 @@ import {
7
7
  FormSelectProps,
8
8
  DropEvent,
9
9
  } from '@patternfly/react-core';
10
- import { SelectOptionProps } from '@patternfly/react-core/deprecated';
10
+ import { DropdownItemProps } from '@patternfly/react-core';
11
11
  import { FieldValidator, FieldHelperProps } from 'formik';
12
12
  import { DropzoneProps } from 'react-dropzone';
13
13
  import { CodeEditorProps } from '@patternfly/react-code-editor';
@@ -44,7 +44,7 @@ export interface SelectFieldProps extends FieldProps {
44
44
  // onBlur?: (event: React.FormEvent<HTMLSelectElement>) => void;
45
45
  }
46
46
 
47
- export type MultiSelectOption = SelectOptionProps & { id: string; displayName: string };
47
+ export type MultiSelectOption = DropdownItemProps & { id: string; displayName: string };
48
48
 
49
49
  export interface MultiSelectFieldProps extends FieldProps {
50
50
  options: MultiSelectOption[];
@@ -14,7 +14,9 @@ export const getHumanizedTime = (dateTime?: string) => {
14
14
  };
15
15
 
16
16
  // TypesScript safe
17
- export const isSelectEventChecked = (event: React.MouseEvent | React.ChangeEvent): boolean => {
18
- const target = event.target as { checked?: boolean };
17
+ export const isSelectEventChecked = (
18
+ event: React.MouseEvent | React.ChangeEvent | undefined,
19
+ ): boolean => {
20
+ const target = event?.target as { checked?: boolean };
19
21
  return !!target?.checked;
20
22
  };
@@ -319,15 +319,13 @@ export const OPERATOR_NAME_KUBE_DESCHEDULER = 'kube-descheduler';
319
319
 
320
320
  export const singleClusterOperators = [
321
321
  OPERATOR_NAME_CNV,
322
- OPERATOR_NAME_NODE_HEALTHCHECK,
323
- OPERATOR_NAME_FENCE_AGENTS_REMEDIATION,
324
- OPERATOR_NAME_NODE_MAINTENANCE,
325
322
  OPERATOR_NAME_MTV,
326
- OPERATOR_NAME_KUBE_DESCHEDULER,
327
323
  OPERATOR_NAME_NMSTATE,
324
+ OPERATOR_NAME_NODE_HEALTHCHECK,
325
+ OPERATOR_NAME_NODE_MAINTENANCE,
326
+ OPERATOR_NAME_FENCE_AGENTS_REMEDIATION,
328
327
  OPERATOR_NAME_SELF_NODE_REMEDIATION,
329
- OPERATOR_NAME_ODF,
330
- OPERATOR_NAME_LSO,
328
+ OPERATOR_NAME_KUBE_DESCHEDULER,
331
329
  ];
332
330
 
333
331
  export const singleClusterBundles = ['virtualization'];
@@ -182,3 +182,6 @@ export const getServiceMeshLink = (ocpVersion?: string) =>
182
182
 
183
183
  export const SERVERLESS_OPERATOR_LINK =
184
184
  'https://docs.openshift.com/serverless/1.28/install/install-serverless-operator.html#serverless-install-web-console_install-serverless-operator';
185
+
186
+ export const KUBECONFIG_INFO_LINK =
187
+ 'https://docs.redhat.com/en/documentation/openshift_container_platform/4.18/html/cli_tools/openshift-cli-oc#about-switches-between-cli-profiles_managing-cli-profiles';
@@ -1,7 +1,3 @@
1
- import './configurations';
2
- import './styles.css';
3
- import './utils';
4
-
5
1
  export * from './components';
6
2
  export * from './api';
7
3
  export * from './types';
@@ -1,6 +1,6 @@
1
1
  import React from 'react';
2
2
  import { Modal, ModalVariant } from '@patternfly/react-core';
3
- import { WizardHeader } from '@patternfly/react-core/deprecated';
3
+ import { WizardHeader } from '@patternfly/react-core';
4
4
  import classNames from 'classnames';
5
5
  import { ClusterWizardStep } from '../../../../common';
6
6
  import { useModalDialogsContext } from '../../hosts/ModalDialogsContext';
@@ -1,5 +1,5 @@
1
1
  import React from 'react';
2
- import { WizardNav, WizardNavItem } from '@patternfly/react-core/deprecated';
2
+ import { WizardNav, WizardNavItem } from '@patternfly/react-core';
3
3
  import { Day2WizardStepsType, day2WizardStepNames, staticIpFormViewSubSteps } from './constants';
4
4
  import { useDay2WizardContext } from './Day2WizardContext';
5
5
  import { isStaticIpStep } from '../../clusterWizard/wizardTransition';
@@ -18,10 +18,10 @@ const Day2WizardNav = () => {
18
18
  const getNavItem = (idx: number, stepId: Day2WizardStepsType): React.ReactNode => {
19
19
  return (
20
20
  <WizardNavItem
21
- step={idx}
21
+ stepIndex={idx}
22
22
  key={stepId}
23
23
  content={day2WizardStepNames[stepId]}
24
- onNavItemClick={() => wizardContext.setCurrentStepId(stepId)}
24
+ onClick={() => wizardContext.setCurrentStepId(stepId)}
25
25
  isCurrent={wizardContext.currentStepId === stepId}
26
26
  isDisabled={isStepDisabled(idx, stepId)}
27
27
  />
@@ -31,14 +31,14 @@ const Day2WizardNav = () => {
31
31
  const getStaticIpFormViewNavItem = (idx: number): React.ReactNode => {
32
32
  return (
33
33
  <WizardNavItem
34
- step={idx}
34
+ stepIndex={idx}
35
35
  isExpandable={true}
36
36
  content="Static network configurations"
37
37
  key="static-network-configuration-form-view"
38
38
  isCurrent={isStaticIpStep(wizardContext.currentStepId)}
39
39
  isDisabled={isStepIdxAfterCurrent(idx)}
40
40
  >
41
- <WizardNav returnList>
41
+ <WizardNav isInnerList>
42
42
  {staticIpFormViewSubSteps.map((stepId, subIdx) => {
43
43
  return getNavItem(idx + subIdx, stepId);
44
44
  })}
@@ -37,7 +37,11 @@ const makeState = (
37
37
  };
38
38
 
39
39
  export const getAddHostsTabState = (cluster: OcmClusterType): AddHostsTabState => {
40
- const isClusterStateReady = /ready|installed/.test(cluster.state);
40
+ // Prioritize aiCluster.status over cluster.state to prevent inconsistencies
41
+ // where metrics might show the cluster as ready while installation is still in progress
42
+ const isClusterStateReady = cluster.aiCluster?.status
43
+ ? /ready|installed/.test(cluster.aiCluster.status)
44
+ : /ready|installed/.test(cluster.state);
41
45
  const wasInstalledUsingAssistedInstaller = cluster.product?.id === 'OCP-AssistedInstall';
42
46
  // Checking if the Day1 cluster has reported metrics, so it can be determined if it's an SNO / multi node and has required information
43
47
  const day1ClusterHostCount = cluster.metrics?.nodes?.total || 0;
@@ -13,7 +13,6 @@ import { useClusterWizardContext } from '../clusterWizard/ClusterWizardContext';
13
13
  import DeleteCustomManifestModal from './manifestsConfiguration/DeleteCustomManifestModal';
14
14
  import { ClustersService } from '../../services';
15
15
  import { ClustersAPI } from '../../services/apis';
16
- import { useLocation } from 'react-router-dom-v5-compat';
17
16
 
18
17
  const Label = () => {
19
18
  return (
@@ -38,18 +37,6 @@ const CustomManifestCheckbox = ({ clusterId, isDisabled }: CustomManifestCheckbo
38
37
  const fieldId = getFieldId(name, 'input');
39
38
  const clusterWizardContext = useClusterWizardContext();
40
39
  const [isDeleteCustomManifestsOpen, setDeleteCustomManifestsOpen] = React.useState(false);
41
- const location = useLocation();
42
-
43
- React.useEffect(() => {
44
- const searchParams = new URLSearchParams(location.search);
45
- const isAssistedMigration = searchParams.get('source') === 'assisted_migration';
46
-
47
- if (isAssistedMigration) {
48
- setValue(true);
49
- clusterWizardContext.setCustomManifestsStep(true);
50
- }
51
- // eslint-disable-next-line react-hooks/exhaustive-deps
52
- }, [location]);
53
40
 
54
41
  const cleanCustomManifests = React.useCallback(async () => {
55
42
  const { data: manifests } = await ClustersAPI.getManifests(clusterId);