Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Wizard: Debounce unique validation (HMS-4581) #2374

Merged
merged 1 commit into from
Aug 29, 2024
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension

Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
47 changes: 30 additions & 17 deletions src/Components/CreateImageWizard/utilities/useValidation.tsx
Original file line number Diff line number Diff line change
@@ -1,5 +1,6 @@
import { useEffect, useState } from 'react';

import { UNIQUE_VALIDATION_DELAY } from '../../../constants';
import { useAppSelector } from '../../../store/hooks';
import {
BlueprintsResponse,
Expand Down Expand Up @@ -86,24 +87,35 @@ export function useDetailsValidation(): StepValidation {

const [trigger] = useLazyGetBlueprintsQuery();

// Debounce the API call to check if the name is unique
useEffect(() => {
if (name !== '' && nameValid) {
trigger({ name })
.unwrap()
.then((response: BlueprintsResponse) => {
if (
response?.meta?.count > 0 &&
response.data[0].id !== blueprintId
) {
setUniqueName(false);
} else {
setUniqueName(true);
}
})
.catch(() => {
// If the request fails, we assume the name is unique
setUniqueName(true);
});
const timer = setTimeout(
() => {
setUniqueName(null);
trigger({ name })
.unwrap()
.then((response: BlueprintsResponse) => {
if (
response?.meta?.count > 0 &&
response.data[0].id !== blueprintId
) {
setUniqueName(false);
} else {
setUniqueName(true);
}
})
.catch(() => {
// If the request fails, we assume the name is unique
setUniqueName(true);
});
},
UNIQUE_VALIDATION_DELAY // If name is empty string, instantly return
);

return () => {
clearTimeout(timer);
};
}
}, [blueprintId, name, setUniqueName, trigger, nameValid]);

Expand All @@ -122,6 +134,7 @@ export function useDetailsValidation(): StepValidation {
name: nameError,
description: descriptionValid ? '' : 'Invalid description',
},
disabledNext: !!nameError || !descriptionValid,
// if uniqueName is null, we are still waiting for the API response
disabledNext: !!nameError || !descriptionValid || uniqueName !== true,
};
}
1 change: 1 addition & 0 deletions src/constants.ts
Original file line number Diff line number Diff line change
Expand Up @@ -214,6 +214,7 @@ export const EPEL_9_REPO_DEFINITION = {
};

export const DEBOUNCED_SEARCH_WAIT_TIME = 500;
export const UNIQUE_VALIDATION_DELAY = 300;
export const FIRST_BOOT_SERVICE_DATA =
'W1VuaXRdCkRlc2NyaXB0aW9uPVJ1biBmaXJzdCBib290IHNjcmlwdApDb25kaXRpb25QYXRoRXhpc3RzPS91c3IvbG9jYWwvc2Jpbi9jdXN0b20tZmlyc3QtYm9vdApXYW50cz1uZXR3b3JrLW9ubGluZS50YXJnZXQKQWZ0ZXI9bmV0d29yay1vbmxpbmUudGFyZ2V0CkFmdGVyPW9zYnVpbGQtZmlyc3QtYm9vdC5zZXJ2aWNlCgpbU2VydmljZV0KVHlwZT1vbmVzaG90CkV4ZWNTdGFydD0vdXNyL2xvY2FsL3NiaW4vY3VzdG9tLWZpcnN0LWJvb3QKRXhlY1N0YXJ0UG9zdD1tdiAvdXNyL2xvY2FsL3NiaW4vY3VzdG9tLWZpcnN0LWJvb3QgL3Vzci9sb2NhbC9zYmluL2N1c3RvbS1maXJzdC1ib290LmRvbmUKCltJbnN0YWxsXQpXYW50ZWRCeT1tdWx0aS11c2VyLnRhcmdldAo=';

Expand Down
9 changes: 9 additions & 0 deletions src/test/setup.ts
Original file line number Diff line number Diff line change
Expand Up @@ -39,6 +39,15 @@ vi.mock('@redhat-cloud-services/frontend-components/useChrome', () => ({
}),
}));

vi.mock(import('../../src/constants'), async (importOriginal) => {
const mod = await importOriginal(); // type is inferred
return {
...mod,
// replace some exports
UNIQUE_VALIDATION_DELAY: 0,
};
});

vi.mock('@unleash/proxy-client-react', () => ({
useUnleashContext: () => vi.fn(),
useFlag: vi.fn((flag) => {
Expand Down
Loading