cloudConfig: toggle aws config

This is still a wip since the form fields aren't yet disabled when the
config toggle is set to off.
This commit is contained in:
Gianluca Zuccarelli 2025-04-16 10:56:15 +00:00 committed by Sanne Raymaekers
parent 73ffb97414
commit afcc0126e4
2 changed files with 112 additions and 19 deletions

View file

@ -1,69 +1,153 @@
import React from 'react'; import React, { useState } from 'react';
import { Form, FormGroup } from '@patternfly/react-core'; import { Form, FormGroup, Switch, TextInput } from '@patternfly/react-core';
import { isAwsBucketValid, isAwsCredsPathValid } from './validators'; import { isAwsBucketValid, isAwsCredsPathValid } from './validators';
import { import {
changeAWSBucketName, changeAWSBucketName,
changeAWSCredsPath, changeAWSCredsPath,
reinitializeAWSConfig,
selectAWSBucketName, selectAWSBucketName,
selectAWSCredsPath, selectAWSCredsPath,
} from '../../store/cloudProviderConfigSlice'; } from '../../store/cloudProviderConfigSlice';
import {
AWSWorkerConfig,
WorkerConfigResponse,
} from '../../store/cockpit/types';
import { useAppDispatch, useAppSelector } from '../../store/hooks'; import { useAppDispatch, useAppSelector } from '../../store/hooks';
import { ValidatedInput } from '../CreateImageWizard/ValidatedInput'; import { ValidatedInput } from '../CreateImageWizard/ValidatedInput';
type FormGroupProps = { type FormGroupProps<T> = {
value: string | undefined; value: T | undefined;
setValue: (value: string) => void; onChange: (value: T) => void;
isDisabled?: boolean;
}; };
const AWSBucket = ({ value, setValue }: FormGroupProps) => { type ToggleGroupProps = Omit<FormGroupProps<boolean>, 'isDisabled'>;
const AWSConfigToggle = ({ value, onChange }: ToggleGroupProps) => {
const handleChange = (
_event: React.FormEvent<HTMLInputElement>,
checked: boolean
) => {
onChange(checked);
};
return ( return (
<FormGroup label="AWS Bucket"> <FormGroup label="Configure AWS Uploads">
<Switch
id="aws-config-switch"
ouiaId="aws-config-switch"
aria-label="aws-config-switch"
// empty label so there is no icon
label=""
isChecked={value}
onChange={handleChange}
/>
</FormGroup>
);
};
const DisabledInputGroup = ({
value,
label,
}: {
value: string | undefined;
label: string;
}) => {
return (
<FormGroup label={label}>
<TextInput aria-label={label} value={value || ''} isDisabled />
</FormGroup>
);
};
const AWSBucket = ({ value, onChange, isDisabled }: FormGroupProps<string>) => {
const label = 'AWS Bucket';
if (isDisabled) {
return <DisabledInputGroup label={label} value={value} />;
}
return (
<FormGroup label={label}>
<ValidatedInput <ValidatedInput
ariaLabel="aws-bucket" ariaLabel="aws-bucket"
value={value || ''} value={value || ''}
validator={isAwsBucketValid} validator={isAwsBucketValid}
onChange={(_event, value) => setValue(value)} onChange={(_event, value) => onChange(value)}
helperText="Invalid AWS bucket name" helperText="Invalid AWS bucket name"
/> />
</FormGroup> </FormGroup>
); );
}; };
const AWSCredsPath = ({ value, setValue }: FormGroupProps) => { const AWSCredsPath = ({
value,
onChange,
isDisabled,
}: FormGroupProps<string>) => {
const label = 'AWS Credentials Filepath';
if (isDisabled) {
return <DisabledInputGroup value={value} label={label} />;
}
return ( return (
<FormGroup label="AWS Credentials Filepath"> <FormGroup label={label}>
<ValidatedInput <ValidatedInput
ariaLabel="aws-creds-path" ariaLabel="aws-creds-path"
value={value || ''} value={value || ''}
validator={isAwsCredsPathValid} validator={isAwsCredsPathValid}
onChange={(_event, value) => setValue(value)} onChange={(_event, value) => onChange(value)}
helperText="Invalid filepath for AWS credentials" helperText="Invalid filepath for AWS credentials"
/> />
</FormGroup> </FormGroup>
); );
}; };
export const AWSConfig = () => { type AWSConfigProps = {
isEnabled: boolean;
reinit: (config: AWSWorkerConfig | undefined) => void;
refetch: () => Promise<{
data?: WorkerConfigResponse | undefined;
}>;
};
export const AWSConfig = ({ isEnabled, refetch, reinit }: AWSConfigProps) => {
const dispatch = useAppDispatch(); const dispatch = useAppDispatch();
const bucket = useAppSelector(selectAWSBucketName); const bucket = useAppSelector(selectAWSBucketName);
const credentials = useAppSelector(selectAWSCredsPath); const credentials = useAppSelector(selectAWSCredsPath);
const [enabled, setEnabled] = useState<boolean>(isEnabled);
// TODO: maybe add a radio button to toggle AWS configuration const onToggle = async (v: boolean) => {
// on or off - this might simplify validation & the overall if (v) {
// experience try {
const { data } = await refetch();
reinit(data?.aws);
setEnabled(v);
return;
} catch {
return;
}
}
dispatch(reinitializeAWSConfig());
setEnabled(v);
};
return ( return (
<Form> <Form>
<AWSConfigToggle value={enabled} onChange={onToggle} />
<AWSBucket <AWSBucket
value={bucket} value={bucket}
setValue={(v) => dispatch(changeAWSBucketName(v))} onChange={(v) => dispatch(changeAWSBucketName(v))}
isDisabled={!enabled}
/> />
<AWSCredsPath <AWSCredsPath
value={credentials} value={credentials}
setValue={(v) => dispatch(changeAWSCredsPath(v))} onChange={(v) => dispatch(changeAWSCredsPath(v))}
isDisabled={!enabled}
/> />
</Form> </Form>
); );

View file

@ -8,6 +8,7 @@ import {
EmptyStateFooter, EmptyStateFooter,
EmptyStateVariant, EmptyStateVariant,
PageSection, PageSection,
Skeleton,
Title, Title,
Wizard, Wizard,
WizardStep, WizardStep,
@ -63,7 +64,7 @@ export const CloudProviderConfig = () => {
const dispatch = useAppDispatch(); const dispatch = useAppDispatch();
const handleClose = () => navigate(resolveRelPath('')); const handleClose = () => navigate(resolveRelPath(''));
const { data, error } = useGetWorkerConfigQuery({}); const { data, error, refetch, isLoading } = useGetWorkerConfigQuery({});
const initAWSConfig = useCallback( const initAWSConfig = useCallback(
(config: AWSWorkerConfig | undefined) => { (config: AWSWorkerConfig | undefined) => {
@ -88,6 +89,10 @@ export const CloudProviderConfig = () => {
initAWSConfig(data?.aws); initAWSConfig(data?.aws);
}, [data, initAWSConfig]); }, [data, initAWSConfig]);
if (isLoading) {
return <Skeleton />;
}
if (error) { if (error) {
return <ConfigError onClose={handleClose} />; return <ConfigError onClose={handleClose} />;
} }
@ -106,7 +111,11 @@ export const CloudProviderConfig = () => {
isBackDisabled: true, isBackDisabled: true,
}} }}
> >
<AWSConfig /> <AWSConfig
refetch={refetch}
reinit={initAWSConfig}
isEnabled={!!(data?.aws && Object.keys(data.aws).length > 0)}
/>
</WizardStep> </WizardStep>
</Wizard> </Wizard>
</PageSection> </PageSection>