WizardV2: Validate steps through redux state
Store validation status in redux state. This is bit complex on the redux side, but pretty simple on the components. It allows for reuse of the validation state instead of revalidating wherever needed.
This commit is contained in:
parent
be5311e66a
commit
709ae39d23
8 changed files with 204 additions and 19 deletions
|
|
@ -17,7 +17,7 @@ import {
|
|||
selectBlueprintDescription,
|
||||
selectBlueprintName,
|
||||
} from '../../../../store/wizardSlice';
|
||||
import { ValidatedTextInput } from '../../ValidatedTextInput';
|
||||
import { StateValidatedInput } from '../../ValidatedTextInput';
|
||||
import {
|
||||
isBlueprintDescriptionValid,
|
||||
isBlueprintNameValid,
|
||||
|
|
@ -52,9 +52,11 @@ const DetailsStep = () => {
|
|||
blueprint.
|
||||
</Text>
|
||||
<FormGroup isRequired label="Blueprint name" fieldId="blueprint-name">
|
||||
<ValidatedTextInput
|
||||
<StateValidatedInput
|
||||
ariaLabel="blueprint name"
|
||||
dataTestId="blueprint"
|
||||
stepId="details"
|
||||
inputId="blueprint-name"
|
||||
value={blueprintName}
|
||||
validator={isBlueprintNameValid}
|
||||
onChange={handleNameChange}
|
||||
|
|
@ -74,9 +76,11 @@ const DetailsStep = () => {
|
|||
label="Blueprint description"
|
||||
fieldId="blueprint-description-name"
|
||||
>
|
||||
<ValidatedTextInput
|
||||
<StateValidatedInput
|
||||
ariaLabel="blueprint description"
|
||||
dataTestId="blueprint description"
|
||||
stepId="details"
|
||||
inputId="blueprint-description"
|
||||
value={blueprintDescription || ''}
|
||||
validator={isBlueprintDescriptionValid}
|
||||
onChange={handleDescriptionChange}
|
||||
|
|
|
|||
|
|
@ -18,11 +18,13 @@ import {
|
|||
type CreateDropdownProps = {
|
||||
getBlueprintPayload: () => Promise<'' | CreateBlueprintRequest | undefined>;
|
||||
setIsOpen: (isOpen: boolean) => void;
|
||||
isDisabled?: boolean;
|
||||
};
|
||||
|
||||
export const CreateSaveAndBuildBtn = ({
|
||||
getBlueprintPayload,
|
||||
setIsOpen,
|
||||
isDisabled,
|
||||
}: CreateDropdownProps) => {
|
||||
const [buildBlueprint] = useComposeBlueprintMutation();
|
||||
const [createBlueprint] = useCreateBlueprintMutation({
|
||||
|
|
@ -42,7 +44,11 @@ export const CreateSaveAndBuildBtn = ({
|
|||
|
||||
return (
|
||||
<DropdownList>
|
||||
<DropdownItem onClick={onSaveAndBuild} ouiaId="wizard-create-build-btn">
|
||||
<DropdownItem
|
||||
onClick={onSaveAndBuild}
|
||||
ouiaId="wizard-create-build-btn"
|
||||
isDisabled={isDisabled}
|
||||
>
|
||||
Create blueprint and build image(s)
|
||||
</DropdownItem>
|
||||
</DropdownList>
|
||||
|
|
@ -52,6 +58,7 @@ export const CreateSaveAndBuildBtn = ({
|
|||
export const CreateSaveButton = ({
|
||||
setIsOpen,
|
||||
getBlueprintPayload,
|
||||
isDisabled,
|
||||
}: CreateDropdownProps) => {
|
||||
const [createBlueprint, { isLoading }] = useCreateBlueprintMutation({
|
||||
fixedCacheKey: 'createBlueprintKey',
|
||||
|
|
@ -62,7 +69,11 @@ export const CreateSaveButton = ({
|
|||
requestBody && createBlueprint({ createBlueprintRequest: requestBody });
|
||||
};
|
||||
return (
|
||||
<MenuToggleAction onClick={onSave} id="wizard-create-save-btn">
|
||||
<MenuToggleAction
|
||||
onClick={onSave}
|
||||
id="wizard-create-save-btn"
|
||||
isDisabled={isDisabled}
|
||||
>
|
||||
<Flex display={{ default: 'inlineFlex' }}>
|
||||
{isLoading && (
|
||||
<FlexItem>
|
||||
|
|
|
|||
|
|
@ -19,12 +19,14 @@ type EditDropdownProps = {
|
|||
getBlueprintPayload: () => Promise<'' | CreateBlueprintRequest | undefined>;
|
||||
setIsOpen: (isOpen: boolean) => void;
|
||||
blueprintId: string;
|
||||
isDisabled?: boolean;
|
||||
};
|
||||
|
||||
export const EditSaveAndBuildBtn = ({
|
||||
getBlueprintPayload,
|
||||
setIsOpen,
|
||||
blueprintId,
|
||||
isDisabled,
|
||||
}: EditDropdownProps) => {
|
||||
const [buildBlueprint] = useComposeBlueprintMutation();
|
||||
const [updateBlueprint] = useUpdateBlueprintMutation({
|
||||
|
|
@ -44,7 +46,11 @@ export const EditSaveAndBuildBtn = ({
|
|||
|
||||
return (
|
||||
<DropdownList>
|
||||
<DropdownItem onClick={onSaveAndBuild} ouiaId="wizard-edit-build-btn">
|
||||
<DropdownItem
|
||||
onClick={onSaveAndBuild}
|
||||
ouiaId="wizard-edit-build-btn"
|
||||
isDisabled={isDisabled}
|
||||
>
|
||||
Save changes and build image(s)
|
||||
</DropdownItem>
|
||||
</DropdownList>
|
||||
|
|
@ -55,6 +61,7 @@ export const EditSaveButton = ({
|
|||
setIsOpen,
|
||||
getBlueprintPayload,
|
||||
blueprintId,
|
||||
isDisabled,
|
||||
}: EditDropdownProps) => {
|
||||
const [updateBlueprint, { isLoading }] = useUpdateBlueprintMutation({
|
||||
fixedCacheKey: 'updateBlueprintKey',
|
||||
|
|
@ -66,7 +73,11 @@ export const EditSaveButton = ({
|
|||
updateBlueprint({ id: blueprintId, createBlueprintRequest: requestBody });
|
||||
};
|
||||
return (
|
||||
<MenuToggleAction onClick={onSave} id="wizard-edit-save-btn">
|
||||
<MenuToggleAction
|
||||
onClick={onSave}
|
||||
id="wizard-edit-save-btn"
|
||||
isDisabled={isDisabled}
|
||||
>
|
||||
<Flex display={{ default: 'inlineFlex' }}>
|
||||
{isLoading && (
|
||||
<FlexItem>
|
||||
|
|
|
|||
|
|
@ -15,11 +15,12 @@ import { useNavigate, useParams } from 'react-router-dom';
|
|||
import { CreateSaveAndBuildBtn, CreateSaveButton } from './CreateDropdown';
|
||||
import { EditSaveAndBuildBtn, EditSaveButton } from './EditDropdown';
|
||||
|
||||
import { useServerStore } from '../../../../../store/hooks';
|
||||
import { useServerStore, useAppSelector } from '../../../../../store/hooks';
|
||||
import {
|
||||
useCreateBlueprintMutation,
|
||||
useUpdateBlueprintMutation,
|
||||
} from '../../../../../store/imageBuilderApi';
|
||||
import { selectIsValid } from '../../../../../store/wizardSlice';
|
||||
import { resolveRelPath } from '../../../../../Utilities/path';
|
||||
import { mapRequestFromState } from '../../../utilities/requestMapper';
|
||||
|
||||
|
|
@ -40,6 +41,7 @@ const ReviewWizardFooter = () => {
|
|||
setIsOpen(!isOpen);
|
||||
};
|
||||
const navigate = useNavigate();
|
||||
const isValid = useAppSelector(selectIsValid);
|
||||
|
||||
useEffect(() => {
|
||||
if (isUpdateSuccess || isCreateSuccess) {
|
||||
|
|
@ -68,6 +70,7 @@ const ReviewWizardFooter = () => {
|
|||
ref={toggleRef}
|
||||
onClick={onToggleClick}
|
||||
isExpanded={isOpen}
|
||||
isDisabled={!isValid}
|
||||
splitButtonOptions={{
|
||||
variant: 'action',
|
||||
items: composeId
|
||||
|
|
@ -77,6 +80,7 @@ const ReviewWizardFooter = () => {
|
|||
getBlueprintPayload={getBlueprintPayload}
|
||||
setIsOpen={setIsOpen}
|
||||
blueprintId={composeId}
|
||||
isDisabled={!isValid}
|
||||
/>,
|
||||
]
|
||||
: [
|
||||
|
|
@ -84,6 +88,7 @@ const ReviewWizardFooter = () => {
|
|||
key="wizard-create-save-btn"
|
||||
getBlueprintPayload={getBlueprintPayload}
|
||||
setIsOpen={setIsOpen}
|
||||
isDisabled={!isValid}
|
||||
/>,
|
||||
],
|
||||
}}
|
||||
|
|
@ -99,11 +104,13 @@ const ReviewWizardFooter = () => {
|
|||
getBlueprintPayload={getBlueprintPayload}
|
||||
setIsOpen={setIsOpen}
|
||||
blueprintId={composeId}
|
||||
isDisabled={!isValid}
|
||||
/>
|
||||
) : (
|
||||
<CreateSaveAndBuildBtn
|
||||
getBlueprintPayload={getBlueprintPayload}
|
||||
setIsOpen={setIsOpen}
|
||||
isDisabled={!isValid}
|
||||
/>
|
||||
)}
|
||||
</Dropdown>
|
||||
|
|
|
|||
Loading…
Add table
Add a link
Reference in a new issue