diff --git a/src/hooks.js b/src/hooks.js
index c162608243..483024e67c 100644
--- a/src/hooks.js
+++ b/src/hooks.js
@@ -32,26 +32,3 @@ export const useEscapeClick = ({ onEscape, dependency }) => {
};
}, [dependency]);
};
-
-/**
- * Custom hook to debounce a string value.
- *
- * @param {string} value - The string value to be debounced.
- * @param {number} [delay=500] - The delay in milliseconds before updating the debounced value.
- * @returns {string} The debounced string value.
- */
-export const useDebounce = (value, delay = 500) => {
- const [debouncedValue, setDebouncedValue] = useState(value);
-
- useEffect(() => {
- const timer = setTimeout(() => {
- setDebouncedValue(value);
- }, delay);
-
- return () => {
- clearTimeout(timer);
- };
- }, [value, delay]);
-
- return debouncedValue;
-};
diff --git a/src/studio-home/__mocks__/studioHomeMock.js b/src/studio-home/__mocks__/studioHomeMock.js
index 0de8903c80..5385201e52 100644
--- a/src/studio-home/__mocks__/studioHomeMock.js
+++ b/src/studio-home/__mocks__/studioHomeMock.js
@@ -47,7 +47,7 @@ module.exports = {
org: 'org.0',
rerunLink: null,
run: 'Run_0',
- url: null,
+ url: '',
},
],
inProcessCourseActions: [],
diff --git a/src/studio-home/processing-courses/index.jsx b/src/studio-home/processing-courses/index.jsx
index 10fc02d1cf..67003659c6 100644
--- a/src/studio-home/processing-courses/index.jsx
+++ b/src/studio-home/processing-courses/index.jsx
@@ -13,7 +13,7 @@ const ProcessingCourses = () => {
return (
<>
-
+
{intl.formatMessage(messages.processingTitle)}
diff --git a/src/studio-home/tabs-section/courses-tab/courses-filters/index.jsx b/src/studio-home/tabs-section/courses-tab/courses-filters/index.jsx
index 61847a3d7a..a1939681b8 100644
--- a/src/studio-home/tabs-section/courses-tab/courses-filters/index.jsx
+++ b/src/studio-home/tabs-section/courses-tab/courses-filters/index.jsx
@@ -131,7 +131,7 @@ const CoursesFilters = ({
onClear={handleClearSearchInput}
/>
{isLoading && (
-
+
)}
diff --git a/src/studio-home/tabs-section/courses-tab/courses-filters/index.test.jsx b/src/studio-home/tabs-section/courses-tab/courses-filters/index.test.jsx
index fdd41b12ce..76f521670b 100644
--- a/src/studio-home/tabs-section/courses-tab/courses-filters/index.test.jsx
+++ b/src/studio-home/tabs-section/courses-tab/courses-filters/index.test.jsx
@@ -126,4 +126,44 @@ describe('CoursesFilters', () => {
userEvent.type(searchInput, 'testing{enter}');
expect(handleSubmit).toHaveBeenCalled();
});
+
+ it('should call dispatch after debounce delay when the search input changes', async () => {
+ renderComponent();
+ const searchInput = screen.getByRole('searchbox');
+ fireEvent.change(searchInput, { target: { value: 'test' } });
+ await waitFor(() => expect(dispatchMock).toHaveBeenCalled(), { timeout: 500 });
+ expect(dispatchMock).toHaveBeenCalledWith(expect.anything());
+ });
+
+ it('should not call dispatch when the search input contains only spaces', async () => {
+ renderComponent();
+ const searchInput = screen.getByRole('searchbox');
+ fireEvent.change(searchInput, { target: { value: ' ' } });
+ await new Promise((r) => setTimeout(r, 500));
+
+ expect(dispatchMock).not.toHaveBeenCalled();
+ });
+
+ it('should display the loading spinner when isLoading is true', () => {
+ renderComponent({ isLoading: true });
+ const spinner = screen.getByTestId('loading-search-spinner');
+ expect(spinner).toBeInTheDocument();
+ });
+
+ it('should not display the loading spinner when isLoading is false', () => {
+ renderComponent({ isLoading: false });
+ const spinner = screen.queryByTestId('loading-search-spinner');
+ expect(spinner).not.toBeInTheDocument();
+ });
+
+ it('should clear the search input and call dispatch when the reset button is clicked', async () => {
+ renderComponent();
+ const searchInput = screen.getByRole('searchbox');
+ fireEvent.change(searchInput, { target: { value: 'test' } });
+ const form = searchInput.closest('form');
+ const resetButton = form.querySelector('button[type="reset"]');
+ fireEvent.click(resetButton);
+ expect(searchInput.value).toBe('');
+ expect(dispatchMock).toHaveBeenCalled();
+ });
});
diff --git a/src/studio-home/tabs-section/courses-tab/index.test.jsx b/src/studio-home/tabs-section/courses-tab/index.test.jsx
index ba5cea3f70..3c4811edc0 100644
--- a/src/studio-home/tabs-section/courses-tab/index.test.jsx
+++ b/src/studio-home/tabs-section/courses-tab/index.test.jsx
@@ -103,7 +103,6 @@ describe('', () => {
const props = { isFailed: true };
const customStoreData = { studioHomeCoursesRequestParams: { currentPage: 1, isFiltered: false } };
renderComponent(props, customStoreData);
- screen.debug();
const alertErrorFailed = screen.queryByTestId('error-failed-message');
expect(alertErrorFailed).toBeInTheDocument();
});
@@ -112,8 +111,23 @@ describe('', () => {
const props = { isLoading: false, coursesDataItems: [] };
const customStoreData = { studioHomeCoursesRequestParams: { currentPage: 1, isFiltered: true } };
renderComponent(props, customStoreData);
- screen.debug();
const alertCoursesNotFound = screen.queryByTestId('courses-not-found-alert');
expect(alertCoursesNotFound).toBeInTheDocument();
});
+
+ it('should render processing courses component when isEnabledPagination is false and isShowProcessing is true', () => {
+ const props = { isShowProcessing: true, isEnabledPagination: false };
+ const customStoreData = {
+ studioHomeData: {
+ inProcessCourseActions: [],
+ },
+ studioHomeCoursesRequestParams: {
+ currentPage: 1,
+ isFiltered: true,
+ },
+ };
+ renderComponent(props, customStoreData);
+ const alertCoursesNotFound = screen.queryByTestId('processing-courses-title');
+ expect(alertCoursesNotFound).toBeInTheDocument();
+ });
});