Skip to content

Commit

Permalink
Merge pull request #1036 from sgratch/vsphere-create-form-help-text-v…
Browse files Browse the repository at this point in the history
…alidation-fixes

🐞 Fix few issues with field validations in the vSphere create form
  • Loading branch information
yaacov authored Apr 9, 2024
2 parents bc7a452 + 344215d commit 5575a81
Show file tree
Hide file tree
Showing 11 changed files with 71 additions and 61 deletions.
Original file line number Diff line number Diff line change
Expand Up @@ -4,6 +4,6 @@ export function safeBase64Decode(value: string) {
try {
return Base64.decode(value);
} catch {
return '';
return undefined;
}
}
Original file line number Diff line number Diff line change
Expand Up @@ -12,7 +12,7 @@ import { validateNoSpaces, validatePublicCert, ValidationMsg } from '../../commo
* 'error' - The field's value has failed validation.
*/
export const openstackSecretFieldValidator = (id: string, value: string): ValidationMsg => {
const trimmedValue = value.trim();
const trimmedValue = value?.trim();

let validationState: ValidationMsg;

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -13,7 +13,7 @@ import { validateNoSpaces, validatePublicCert, ValidationMsg } from '../../commo
* 'warning' - The field's value has passed validation but does not fit the standard format, it's the user's choice if to accept that value.
*/
export const esxiSecretFieldValidator = (id: string, value: string): ValidationMsg => {
const trimmedValue = value?.trim() || '';
const trimmedValue = value?.trim();

let validationState: ValidationMsg;

Expand Down Expand Up @@ -41,6 +41,13 @@ export const esxiSecretFieldValidator = (id: string, value: string): ValidationM
const validateUser = (value: string): ValidationMsg => {
const noSpaces = validateNoSpaces(value);

if (value === undefined) {
return {
type: 'default',
msg: 'A username and domain for the ESXi API endpoint, for example: user . [required]',
};
}

if (value === '') {
return {
type: 'error',
Expand All @@ -61,6 +68,13 @@ const validateUser = (value: string): ValidationMsg => {
const validatePassword = (value: string): ValidationMsg => {
const valid = validateNoSpaces(value);

if (value === undefined) {
return {
type: 'default',
msg: 'A user password for connecting to the ESXi API endpoint. [required]',
};
}

if (value === '') {
return {
type: 'error',
Expand Down
Original file line number Diff line number Diff line change
@@ -1,6 +1,13 @@
import { validateURL, ValidationMsg } from '../../common';

export const validateEsxiURL = (url: string | number): ValidationMsg => {
if (url === undefined) {
return {
type: 'default',
msg: 'The URL is required, URL of the ESXi API endpoint for example: https://host-example.com/sdk .',
};
}

// Sanity check
if (typeof url !== 'string') {
return { type: 'error', msg: 'URL is not a string' };
Expand Down
Original file line number Diff line number Diff line change
@@ -1,6 +1,13 @@
import { validateURL, ValidationMsg } from '../../common';

export const validateVCenterURL = (url: string | number): ValidationMsg => {
if (url === undefined) {
return {
type: 'default',
msg: 'The URL is required, URL of the vCenter API endpoint for example: https://host-example.com/sdk .',
};
}

// Sanity check
if (typeof url !== 'string') {
return { type: 'error', msg: 'URL is not a string' };
Expand Down
Original file line number Diff line number Diff line change
@@ -1,6 +1,12 @@
import { validateContainerImage, ValidationMsg } from '../../common';

export const validateVDDKImage = (vddkImage: string | number): ValidationMsg => {
if (vddkImage === undefined)
return {
msg: 'The VDDK image is empty, it is recommended to provide an image, for example: quay.io/kubev2v/vddk:latest .',
type: 'default',
};

// Sanity check
if (typeof vddkImage !== 'string') {
return { type: 'error', msg: 'VDDK image is not a string' };
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -18,7 +18,7 @@ import {
* 'warning' - The field's value has passed validation but does not fit the standard format, it's the user's choice if to accept that value.
*/
export const vcenterSecretFieldValidator = (id: string, value: string): ValidationMsg => {
const trimmedValue = value?.trim() || '';
const trimmedValue = value?.trim();

let validationState: ValidationMsg;

Expand Down Expand Up @@ -46,6 +46,13 @@ export const vcenterSecretFieldValidator = (id: string, value: string): Validati
const validateUser = (value: string): ValidationMsg => {
const noSpaces = validateNoSpaces(value);

if (value === undefined) {
return {
type: 'default',
msg: 'A username and domain for the vCenter API endpoint, for example: [email protected]. [required]',
};
}

if (value === '') {
return {
type: 'error',
Expand Down Expand Up @@ -75,6 +82,13 @@ const validateUser = (value: string): ValidationMsg => {
const validatePassword = (value: string): ValidationMsg => {
const valid = validateNoSpaces(value);

if (value === undefined) {
return {
type: 'default',
msg: 'A user password for connecting to the vCenter API endpoint. [required]',
};
}

if (value === '') {
return {
type: 'error',
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -21,8 +21,8 @@ export const EsxiProviderCreateForm: React.FC<EsxiProviderCreateFormProps> = ({
}) => {
const { t } = useForkliftTranslation();

const url = provider?.spec?.url || '';
const vddkInitImage = provider?.spec?.settings?.['vddkInitImage'] || '';
const url = provider?.spec?.url;
const vddkInitImage = provider?.spec?.settings?.['vddkInitImage'];
const sdkEndpoint = provider?.spec?.settings?.['sdkEndpoint'] || '';

const vddkHelperTextPopover = (
Expand All @@ -44,14 +44,8 @@ export const EsxiProviderCreateForm: React.FC<EsxiProviderCreateFormProps> = ({

const initialState = {
validation: {
url: {
msg: 'The URL of the ESXi API endpoint for example: https://host-example.com/sdk .',
type: 'default',
},
vddkInitImage: {
type: 'default',
msg: 'VMware Virtual Disk Development Kit (VDDK) image, for example: quay.io/kubev2v/vddk:latest .',
},
url: validateEsxiURL(url),
vddkInitImage: validateVDDKImage(vddkInitImage),
},
};

Expand All @@ -74,7 +68,7 @@ export const EsxiProviderCreateForm: React.FC<EsxiProviderCreateFormProps> = ({

const handleChange = useCallback(
(id, value) => {
const trimmedValue = value.trim();
const trimmedValue = value?.trim();

if (id == 'vddkInitImage') {
const validationState = validateVDDKImage(trimmedValue);
Expand All @@ -87,8 +81,6 @@ export const EsxiProviderCreateForm: React.FC<EsxiProviderCreateFormProps> = ({
onChange({
...provider,
spec: {
type: provider.spec.type,
url: provider.spec.url,
...provider?.spec,
settings: {
...(provider?.spec?.settings as object),
Expand All @@ -101,17 +93,9 @@ export const EsxiProviderCreateForm: React.FC<EsxiProviderCreateFormProps> = ({
if (id == 'sdkEndpoint') {
const sdkEndpoint = trimmedValue || undefined;

// Revalidate URL - VCenter or ESXi
const trimmedURL = provider?.spec?.url?.trim() || '';
const validationState = validateEsxiURL(trimmedURL);

dispatch({ type: 'SET_FIELD_VALIDATED', payload: { field: 'url', validationState } });

onChange({
...provider,
spec: {
type: provider.spec.type,
url: provider.spec.url,
...provider?.spec,
settings: {
...(provider?.spec?.settings as object),
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -21,9 +21,9 @@ export const VCenterProviderCreateForm: React.FC<VCenterProviderCreateFormProps>
}) => {
const { t } = useForkliftTranslation();

const url = provider?.spec?.url || '';
const vddkInitImage = provider?.spec?.settings?.['vddkInitImage'] || '';
const sdkEndpoint = provider?.spec?.settings?.['sdkEndpoint'] || '';
const url = provider?.spec?.url;
const vddkInitImage = provider?.spec?.settings?.['vddkInitImage'];
const sdkEndpoint = provider?.spec?.settings?.['sdkEndpoint'];

const vddkHelperTextPopover = (
<ForkliftTrans>
Expand All @@ -44,14 +44,8 @@ export const VCenterProviderCreateForm: React.FC<VCenterProviderCreateFormProps>

const initialState = {
validation: {
url: {
msg: 'The URL of the vCenter API endpoint for example: https://host-example.com/sdk .',
type: 'default',
},
vddkInitImage: {
type: 'default',
msg: 'VMware Virtual Disk Development Kit (VDDK) image, for example: quay.io/kubev2v/vddk:latest .',
},
url: validateVCenterURL(url),
vddkInitImage: validateVDDKImage(vddkInitImage),
},
};

Expand All @@ -74,7 +68,7 @@ export const VCenterProviderCreateForm: React.FC<VCenterProviderCreateFormProps>

const handleChange = useCallback(
(id, value) => {
const trimmedValue = value.trim();
const trimmedValue = value?.trim();

if (id == 'vddkInitImage') {
const validationState = validateVDDKImage(trimmedValue);
Expand All @@ -87,8 +81,6 @@ export const VCenterProviderCreateForm: React.FC<VCenterProviderCreateFormProps>
onChange({
...provider,
spec: {
type: provider.spec.type,
url: provider.spec.url,
...provider?.spec,
settings: {
...(provider?.spec?.settings as object),
Expand All @@ -101,17 +93,9 @@ export const VCenterProviderCreateForm: React.FC<VCenterProviderCreateFormProps>
if (id == 'sdkEndpoint') {
const sdkEndpoint = trimmedValue || undefined;

// Revalidate URL - VCenter or ESXi
const trimmedURL = provider?.spec?.url?.trim() || '';
const validationState = validateVCenterURL(trimmedURL);

dispatch({ type: 'SET_FIELD_VALIDATED', payload: { field: 'url', validationState } });

onChange({
...provider,
spec: {
type: provider.spec.type,
url: provider.spec.url,
...provider?.spec,
settings: {
...(provider?.spec?.settings as object),
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -22,9 +22,9 @@ import { EditComponentProps } from '../BaseCredentialsSection';
export const EsxiCredentialsEdit: React.FC<EditComponentProps> = ({ secret, onChange }) => {
const { t } = useForkliftTranslation();

const user = safeBase64Decode(secret?.data?.user || '');
const url = safeBase64Decode(secret?.data?.url || '');
const password = safeBase64Decode(secret?.data?.password || '');
const user = safeBase64Decode(secret?.data?.user);
const password = safeBase64Decode(secret?.data?.password);
const url = safeBase64Decode(secret?.data?.url);
const cacert = safeBase64Decode(secret?.data?.cacert || '');
const insecureSkipVerify = safeBase64Decode(secret?.data?.insecureSkipVerify || '') === 'true';

Expand Down Expand Up @@ -58,10 +58,7 @@ export const EsxiCredentialsEdit: React.FC<EditComponentProps> = ({ secret, onCh
user: esxiSecretFieldValidator('user', user),
password: esxiSecretFieldValidator('password', password),
insecureSkipVerify: { type: 'default', msg: 'Skip certificate validation' },
cacert: {
type: 'default',
msg: 'The Manager CA certificate unless it was replaced by a third-party certificate, in which case, enter the Manager Apache CA certificate.',
},
cacert: esxiSecretFieldValidator('cacert', cacert),
},
};

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -22,9 +22,9 @@ import { EditComponentProps } from '../BaseCredentialsSection';
export const VCenterCredentialsEdit: React.FC<EditComponentProps> = ({ secret, onChange }) => {
const { t } = useForkliftTranslation();

const user = safeBase64Decode(secret?.data?.user || '');
const url = safeBase64Decode(secret?.data?.url || '');
const password = safeBase64Decode(secret?.data?.password || '');
const user = safeBase64Decode(secret?.data?.user);
const password = safeBase64Decode(secret?.data?.password);
const url = safeBase64Decode(secret?.data?.url);
const cacert = safeBase64Decode(secret?.data?.cacert || '');
const insecureSkipVerify = safeBase64Decode(secret?.data?.insecureSkipVerify || '') === 'true';

Expand Down Expand Up @@ -58,10 +58,7 @@ export const VCenterCredentialsEdit: React.FC<EditComponentProps> = ({ secret, o
user: vcenterSecretFieldValidator('user', user),
password: vcenterSecretFieldValidator('password', password),
insecureSkipVerify: { type: 'default', msg: 'Skip certificate validation' },
cacert: {
type: 'default',
msg: 'The Manager CA certificate unless it was replaced by a third-party certificate, in which case, enter the Manager Apache CA certificate.',
},
cacert: vcenterSecretFieldValidator('cacert', cacert),
},
};

Expand Down

0 comments on commit 5575a81

Please sign in to comment.