From 6899ce6cc1f0b5ea19a43a5dec9252c79df8b925 Mon Sep 17 00:00:00 2001 From: Macharia Muguku Date: Thu, 27 Jan 2022 11:41:02 +0300 Subject: [PATCH 1/6] fetch all nested locations for a selected location in the hierarchy tree to be included in fetching download data --- .../components/DownloadClientData/utils.tsx | 51 +++++++++++++++---- 1 file changed, 42 insertions(+), 9 deletions(-) diff --git a/packages/card-support/src/components/DownloadClientData/utils.tsx b/packages/card-support/src/components/DownloadClientData/utils.tsx index b03c7d326..19717abba 100644 --- a/packages/card-support/src/components/DownloadClientData/utils.tsx +++ b/packages/card-support/src/components/DownloadClientData/utils.tsx @@ -2,10 +2,14 @@ import Papaparse from 'papaparse'; import { OpenSRPService } from '@opensrp/server-service'; import { DownloadClientDataFormFields } from '../DownloadClientData'; import { Dispatch, SetStateAction } from 'react'; -import { OPENSRP_URL_CLIENT_SEARCH, APPLICATION_CSV } from '../../constants'; +import { + OPENSRP_URL_CLIENT_SEARCH, + APPLICATION_CSV, + OPENSRP_URL_LOCATION_HIERARCHY, +} from '../../constants'; import { Client } from '../../ducks/clients'; import { downloadFile } from '../../helpers/utils'; -import { ParsedHierarchyNode } from '@opensrp/location-management'; +import { ParsedHierarchyNode, RawOpenSRPHierarchy } from '@opensrp/location-management'; import { sendErrorNotification } from '@opensrp/notifications'; import { Dictionary } from '@onaio/utils'; import lang, { Lang } from '../../lang'; @@ -55,7 +59,7 @@ export const handleCardOrderDateChange = ( * @param setSubmitting - method to set form `isSubmitting` status * @param langObj - tthe lang object */ -export const submitForm = ( +export const submitForm = async ( values: DownloadClientDataFormFields, accessToken: string, opensrpBaseURL: string, @@ -63,7 +67,7 @@ export const submitForm = ( locations: ParsedHierarchyNode[], setSubmitting: (isSubmitting: boolean) => void, langObj: Lang = lang -): void => { +): Promise => { const { clientLocation, cardStatus, cardOrderDate } = values; if (!clientLocation) { @@ -71,12 +75,37 @@ export const submitForm = ( } setSubmitting(true); - const startDate = cardOrderDate[0]; - const endDate = cardOrderDate[1]; - const endPoint = `${OPENSRP_URL_CLIENT_SEARCH}`; - const serve = new serviceClass(accessToken, opensrpBaseURL, endPoint); + + // get location id's of all nested children of a selected jurisdiction + const fetchNestedLocationIds = async (clientLocationId: string) => { + const serve = new serviceClass(accessToken, opensrpBaseURL, OPENSRP_URL_LOCATION_HIERARCHY); + try { + const res: RawOpenSRPHierarchy = await serve.read(clientLocationId); + // parentChildren is an object with keys as parent location ids + // and values as arrays of children location ids + // each children location with children itself has an entry in the object + const nestedLocationIds = Object.values(res.locationsHierarchy.parentChildren); + const flatNestedLocationIds = nestedLocationIds.flat(); + // all keys (nested children location ids) are present as values of the primary location id values (clientLocationId) + // except the primary location id itself - thus the re-add + const flatNestedLocationIdsWithClientLocationId = [ + ...flatNestedLocationIds, + clientLocationId, + ]; + const stringifiedFlatNestedLocationIdsWithClientLocationId = + flatNestedLocationIdsWithClientLocationId.join(','); + return stringifiedFlatNestedLocationIdsWithClientLocationId; + } catch (_) { + sendErrorNotification(langObj.ERROR_OCCURRED); + return ''; + } + }; + + const nestedLocationIds = await fetchNestedLocationIds(clientLocation); + + // add all nested location ids (children of selected location) to the search params let params: Dictionary = { - locationIds: clientLocation, + locationIds: nestedLocationIds, }; if (cardStatus) { @@ -86,6 +115,10 @@ export const submitForm = ( }; } + const startDate = cardOrderDate[0]; + const endDate = cardOrderDate[1]; + const serve = new serviceClass(accessToken, opensrpBaseURL, OPENSRP_URL_CLIENT_SEARCH); + serve .list(params) .then((clients: Client[]) => { From e011b31af03680ef4ed3331c5e32d45902ddef8b Mon Sep 17 00:00:00 2001 From: Macharia Muguku Date: Thu, 27 Jan 2022 11:43:05 +0300 Subject: [PATCH 2/6] update tests - add mock fixture data, add mock response for nested location ids and mocked endpoint call, add test for endpoind fetch failure --- .../tests/__snapshots__/index.test.tsx.snap | 4 -- .../DownloadClientData/tests/fixtures.ts | 27 ++++++- .../DownloadClientData/tests/index.test.tsx | 17 +++-- .../DownloadClientData/tests/utils.test.tsx | 70 +++++++++++-------- 4 files changed, 77 insertions(+), 41 deletions(-) diff --git a/packages/card-support/src/components/DownloadClientData/tests/__snapshots__/index.test.tsx.snap b/packages/card-support/src/components/DownloadClientData/tests/__snapshots__/index.test.tsx.snap index b018a8231..e08f3c31a 100644 --- a/packages/card-support/src/components/DownloadClientData/tests/__snapshots__/index.test.tsx.snap +++ b/packages/card-support/src/components/DownloadClientData/tests/__snapshots__/index.test.tsx.snap @@ -69,10 +69,6 @@ Object { title="All Locations" value="" /> - { it('downloads csv correctly', async () => { fetch.mockOnce(JSON.stringify(fixtures.sampleTeamAssignment)); fetch.mockOnce(JSON.stringify(fixtures.locationHierarchy)); + fetch.mockOnce(JSON.stringify(fixtures.locationHierarchy)); fetch.mockOnce(JSON.stringify([fixtures.mother, fixtures.child1, fixtures.child2])); const queryClient = new QueryClient(); @@ -276,7 +277,8 @@ describe('components/DownloadClientData', () => { expect(fetch.mock.calls.map((res) => res[0])).toEqual([ 'https://unicef-tunisia-stage.smartregister.org/opensrp/security/authenticate', 'https://unicef-tunisia-stage.smartregister.org/opensrp/rest/location/hierarchy/e2b4a441-21b5-4d03-816b-09d45b17cad7?is_jurisdiction=true', - 'https://unicef-tunisia-stage.smartregister.org/opensrp/rest/client/search?locationIds=e2b4a441-21b5-4d03-816b-09d45b17cad7&attribute=card_status:needs_card', + 'https://unicef-tunisia-stage.smartregister.org/opensrp/rest/location/hierarchy/e2b4a441-21b5-4d03-816b-09d45b17cad7', + 'https://unicef-tunisia-stage.smartregister.org/opensrp/rest/client/search?locationIds=325b9549-80fa-4dd0-9cf8-f0538cbebb18,e2b4a441-21b5-4d03-816b-09d45b17cad7,72f8ae88-58c9-40b4-863a-1c7bc6549a8b,52c10f07-6653-470d-9fee-14b0bb111c2a,d309898b-3925-494f-a30c-689222d3fcce,dbacb5dc-c8a3-439d-b407-13ffd570b9ef,27400130-8127-4f54-b14f-e26f20ecae14,14e83edc-5a54-44f5-816e-c96c61b5d911,9c183088-e498-4183-af41-b29bd32d94b6,66c88197-8281-4eb4-ae2e-4a89ae8419ed,1018b255-0889-492c-b5dd-31a50cb3db4d,5d99a60e-126e-4c40-b5ce-439f920de090,9a0e7727-b011-458f-832a-61108b2fe381,70589012-899c-401d-85a1-13fabce26aab,e5631d3e-70c3-4083-ac17-46f9467c6dd5,e447d5bb-8d42-4be4-b91d-b8d185cf81a6,18b3841b-b5b1-4971-93d0-d36ac20c4565,fee237ef-75e8-4ada-b15f-6d1a92633f33,16c58ef5-3b19-4ec2-ba9c-aefac3d08a66,7a663f5e-2619-4a2d-a7df-7250263f47d2,e2b4a441-21b5-4d03-816b-09d45b17cad7&attribute=card_status:needs_card', ]); expect(papaparseMock).toBeCalledWith([fixtures.child1CsvEntry, fixtures.child2CsvEntry], { header: true, @@ -290,6 +292,7 @@ describe('components/DownloadClientData', () => { it('submits if card status is not entered', async () => { fetch.mockOnce(JSON.stringify(fixtures.sampleTeamAssignment)); fetch.mockOnce(JSON.stringify(fixtures.locationHierarchy)); + fetch.mockOnce(JSON.stringify(fixtures.locationHierarchy)); fetch.mockOnce(JSON.stringify([fixtures.mother, fixtures.child1, fixtures.child2])); const queryClient = new QueryClient(); @@ -329,7 +332,8 @@ describe('components/DownloadClientData', () => { expect(fetch.mock.calls.map((res) => res[0])).toEqual([ 'https://unicef-tunisia-stage.smartregister.org/opensrp/security/authenticate', 'https://unicef-tunisia-stage.smartregister.org/opensrp/rest/location/hierarchy/e2b4a441-21b5-4d03-816b-09d45b17cad7?is_jurisdiction=true', - 'https://unicef-tunisia-stage.smartregister.org/opensrp/rest/client/search?locationIds=e2b4a441-21b5-4d03-816b-09d45b17cad7', + 'https://unicef-tunisia-stage.smartregister.org/opensrp/rest/location/hierarchy/e2b4a441-21b5-4d03-816b-09d45b17cad7', + 'https://unicef-tunisia-stage.smartregister.org/opensrp/rest/client/search?locationIds=325b9549-80fa-4dd0-9cf8-f0538cbebb18,e2b4a441-21b5-4d03-816b-09d45b17cad7,72f8ae88-58c9-40b4-863a-1c7bc6549a8b,52c10f07-6653-470d-9fee-14b0bb111c2a,d309898b-3925-494f-a30c-689222d3fcce,dbacb5dc-c8a3-439d-b407-13ffd570b9ef,27400130-8127-4f54-b14f-e26f20ecae14,14e83edc-5a54-44f5-816e-c96c61b5d911,9c183088-e498-4183-af41-b29bd32d94b6,66c88197-8281-4eb4-ae2e-4a89ae8419ed,1018b255-0889-492c-b5dd-31a50cb3db4d,5d99a60e-126e-4c40-b5ce-439f920de090,9a0e7727-b011-458f-832a-61108b2fe381,70589012-899c-401d-85a1-13fabce26aab,e5631d3e-70c3-4083-ac17-46f9467c6dd5,e447d5bb-8d42-4be4-b91d-b8d185cf81a6,18b3841b-b5b1-4971-93d0-d36ac20c4565,fee237ef-75e8-4ada-b15f-6d1a92633f33,16c58ef5-3b19-4ec2-ba9c-aefac3d08a66,7a663f5e-2619-4a2d-a7df-7250263f47d2,e2b4a441-21b5-4d03-816b-09d45b17cad7', ]); expect(papaparseMock).toBeCalledWith([fixtures.child1CsvEntry, fixtures.child2CsvEntry], { header: true, @@ -339,6 +343,7 @@ describe('components/DownloadClientData', () => { it('uses the default location id if location not selected', async () => { fetch.mockOnce(JSON.stringify(fixtures.sampleTeamAssignment)); fetch.mockOnce(JSON.stringify(fixtures.locationHierarchy)); + fetch.mockOnce(JSON.stringify(fixtures.locationHierarchy)); fetch.mockOnce(JSON.stringify([fixtures.mother, fixtures.child1, fixtures.child2])); const queryClient = new QueryClient(); @@ -377,7 +382,8 @@ describe('components/DownloadClientData', () => { expect(fetch.mock.calls.map((res) => res[0])).toEqual([ 'https://unicef-tunisia-stage.smartregister.org/opensrp/security/authenticate', 'https://unicef-tunisia-stage.smartregister.org/opensrp/rest/location/hierarchy/e2b4a441-21b5-4d03-816b-09d45b17cad7?is_jurisdiction=true', - 'https://unicef-tunisia-stage.smartregister.org/opensrp/rest/client/search?locationIds=e2b4a441-21b5-4d03-816b-09d45b17cad7&attribute=card_status:needs_card', + 'https://unicef-tunisia-stage.smartregister.org/opensrp/rest/location/hierarchy/e2b4a441-21b5-4d03-816b-09d45b17cad7', + 'https://unicef-tunisia-stage.smartregister.org/opensrp/rest/client/search?locationIds=325b9549-80fa-4dd0-9cf8-f0538cbebb18,e2b4a441-21b5-4d03-816b-09d45b17cad7,72f8ae88-58c9-40b4-863a-1c7bc6549a8b,52c10f07-6653-470d-9fee-14b0bb111c2a,d309898b-3925-494f-a30c-689222d3fcce,dbacb5dc-c8a3-439d-b407-13ffd570b9ef,27400130-8127-4f54-b14f-e26f20ecae14,14e83edc-5a54-44f5-816e-c96c61b5d911,9c183088-e498-4183-af41-b29bd32d94b6,66c88197-8281-4eb4-ae2e-4a89ae8419ed,1018b255-0889-492c-b5dd-31a50cb3db4d,5d99a60e-126e-4c40-b5ce-439f920de090,9a0e7727-b011-458f-832a-61108b2fe381,70589012-899c-401d-85a1-13fabce26aab,e5631d3e-70c3-4083-ac17-46f9467c6dd5,e447d5bb-8d42-4be4-b91d-b8d185cf81a6,18b3841b-b5b1-4971-93d0-d36ac20c4565,fee237ef-75e8-4ada-b15f-6d1a92633f33,16c58ef5-3b19-4ec2-ba9c-aefac3d08a66,7a663f5e-2619-4a2d-a7df-7250263f47d2,e2b4a441-21b5-4d03-816b-09d45b17cad7&attribute=card_status:needs_card', ]); expect(papaparseMock).toBeCalledWith([fixtures.child1CsvEntry, fixtures.child2CsvEntry], { header: true, @@ -386,8 +392,7 @@ describe('components/DownloadClientData', () => { it('handles fetch error when fetching user data - team assignments', async () => { fetch.mockRejectOnce(() => Promise.reject('API is down')); - fetch.mockOnce(JSON.stringify(fixtures.locationHierarchy)); - fetch.mockOnce(JSON.stringify([fixtures.mother, fixtures.child1, fixtures.child2])); + const notificationErrorMock = jest.spyOn(notifications, 'sendErrorNotification'); // turn retries off - makes fetch fail on first try @@ -422,7 +427,7 @@ describe('components/DownloadClientData', () => { it('handles fetch error when fetching user location hierarchy', async () => { fetch.mockOnce(JSON.stringify(fixtures.sampleTeamAssignment)); fetch.mockRejectOnce(() => Promise.reject('API is down')); - fetch.mockOnce(JSON.stringify([fixtures.mother, fixtures.child1, fixtures.child2])); + const notificationErrorMock = jest.spyOn(notifications, 'sendErrorNotification'); // turn retries off - makes fetch fail on first try diff --git a/packages/card-support/src/components/DownloadClientData/tests/utils.test.tsx b/packages/card-support/src/components/DownloadClientData/tests/utils.test.tsx index 17cbdce30..23e82fdf7 100644 --- a/packages/card-support/src/components/DownloadClientData/tests/utils.test.tsx +++ b/packages/card-support/src/components/DownloadClientData/tests/utils.test.tsx @@ -145,6 +145,7 @@ describe('components/DownloadClientData/utils/submitForm', () => { const setSubmittingMock = jest.fn(); it('submits the form correctly', async () => { + fetch.mockOnce(JSON.stringify(fixtures.locationHierarchy)); fetch.mockResponse(JSON.stringify([fixtures.mother, fixtures.child1, fixtures.child2])); submitForm( @@ -161,16 +162,9 @@ describe('components/DownloadClientData/utils/submitForm', () => { }); expect(setSubmittingMock.mock.calls[0][0]).toEqual(true); - expect(fetch.mock.calls[0]).toEqual([ - `https://unicef-tunisia-stage.smartregister.org/opensrp/rest/client/search?locationIds=${clientLocation}&attribute=card_status:${cardStatus}`, - { - headers: { - accept: 'application/json', - authorization: 'Bearer hunter2', - 'content-type': 'application/json;charset=UTF-8', - }, - method: 'GET', - }, + expect(fetch.mock.calls.map((res) => res[0])).toEqual([ + 'https://unicef-tunisia-stage.smartregister.org/opensrp/rest/location/hierarchy/e2b4a441-21b5-4d03-816b-09d45b17cad7', + 'https://unicef-tunisia-stage.smartregister.org/opensrp/rest/client/search?locationIds=325b9549-80fa-4dd0-9cf8-f0538cbebb18,e2b4a441-21b5-4d03-816b-09d45b17cad7,72f8ae88-58c9-40b4-863a-1c7bc6549a8b,52c10f07-6653-470d-9fee-14b0bb111c2a,d309898b-3925-494f-a30c-689222d3fcce,dbacb5dc-c8a3-439d-b407-13ffd570b9ef,27400130-8127-4f54-b14f-e26f20ecae14,14e83edc-5a54-44f5-816e-c96c61b5d911,9c183088-e498-4183-af41-b29bd32d94b6,66c88197-8281-4eb4-ae2e-4a89ae8419ed,1018b255-0889-492c-b5dd-31a50cb3db4d,5d99a60e-126e-4c40-b5ce-439f920de090,9a0e7727-b011-458f-832a-61108b2fe381,70589012-899c-401d-85a1-13fabce26aab,e5631d3e-70c3-4083-ac17-46f9467c6dd5,e447d5bb-8d42-4be4-b91d-b8d185cf81a6,18b3841b-b5b1-4971-93d0-d36ac20c4565,fee237ef-75e8-4ada-b15f-6d1a92633f33,16c58ef5-3b19-4ec2-ba9c-aefac3d08a66,7a663f5e-2619-4a2d-a7df-7250263f47d2,e2b4a441-21b5-4d03-816b-09d45b17cad7&attribute=card_status:needs_card', ]); expect(setSubmittingMock.mock.calls[1][0]).toEqual(false); @@ -183,8 +177,37 @@ describe('components/DownloadClientData/utils/submitForm', () => { ); }); + it('handles error if fetching Nested Location Ids fails', async () => { + fetch.mockReject(() => Promise.reject('API is down')); + fetch.mockOnce(JSON.stringify(fixtures.locationHierarchy)); + + const notificationErrorMock = jest.spyOn(notifications, 'sendErrorNotification'); + + submitForm( + values, + accessToken, + opensrpBaseURL, + OpenSRPService, + fixtures.locations, + setSubmittingMock + ); + await act(async () => { + await flushPromises(); + }); + expect(setSubmittingMock.mock.calls[0][0]).toEqual(true); + expect(fetch.mock.calls.map((res) => res[0])).toEqual([ + 'https://unicef-tunisia-stage.smartregister.org/opensrp/rest/location/hierarchy/e2b4a441-21b5-4d03-816b-09d45b17cad7', + 'https://unicef-tunisia-stage.smartregister.org/opensrp/rest/client/search?locationIds=325b9549-80fa-4dd0-9cf8-f0538cbebb18,e2b4a441-21b5-4d03-816b-09d45b17cad7,72f8ae88-58c9-40b4-863a-1c7bc6549a8b,52c10f07-6653-470d-9fee-14b0bb111c2a,d309898b-3925-494f-a30c-689222d3fcce,dbacb5dc-c8a3-439d-b407-13ffd570b9ef,27400130-8127-4f54-b14f-e26f20ecae14,14e83edc-5a54-44f5-816e-c96c61b5d911,9c183088-e498-4183-af41-b29bd32d94b6,66c88197-8281-4eb4-ae2e-4a89ae8419ed,1018b255-0889-492c-b5dd-31a50cb3db4d,5d99a60e-126e-4c40-b5ce-439f920de090,9a0e7727-b011-458f-832a-61108b2fe381,70589012-899c-401d-85a1-13fabce26aab,e5631d3e-70c3-4083-ac17-46f9467c6dd5,e447d5bb-8d42-4be4-b91d-b8d185cf81a6,18b3841b-b5b1-4971-93d0-d36ac20c4565,fee237ef-75e8-4ada-b15f-6d1a92633f33,16c58ef5-3b19-4ec2-ba9c-aefac3d08a66,7a663f5e-2619-4a2d-a7df-7250263f47d2,e2b4a441-21b5-4d03-816b-09d45b17cad7&attribute=card_status:needs_card', + ]); + expect(setSubmittingMock.mock.calls[1][0]).toEqual(false); + expect(papaparseMock).not.toHaveBeenCalled(); + expect(notificationErrorMock).toHaveBeenCalledWith(lang.ERROR_OCCURRED); + }); + it('handles error if submission fails', async () => { + fetch.mockOnce(JSON.stringify(fixtures.locationHierarchy)); fetch.mockReject(() => Promise.reject('API is down')); + const notificationErrorMock = jest.spyOn(notifications, 'sendErrorNotification'); submitForm( @@ -199,16 +222,9 @@ describe('components/DownloadClientData/utils/submitForm', () => { await flushPromises(); }); expect(setSubmittingMock.mock.calls[0][0]).toEqual(true); - expect(fetch.mock.calls[0]).toEqual([ - `https://unicef-tunisia-stage.smartregister.org/opensrp/rest/client/search?locationIds=${clientLocation}&attribute=card_status:${cardStatus}`, - { - headers: { - accept: 'application/json', - authorization: 'Bearer hunter2', - 'content-type': 'application/json;charset=UTF-8', - }, - method: 'GET', - }, + expect(fetch.mock.calls.map((res) => res[0])).toEqual([ + 'https://unicef-tunisia-stage.smartregister.org/opensrp/rest/location/hierarchy/e2b4a441-21b5-4d03-816b-09d45b17cad7', + 'https://unicef-tunisia-stage.smartregister.org/opensrp/rest/client/search?locationIds=325b9549-80fa-4dd0-9cf8-f0538cbebb18,e2b4a441-21b5-4d03-816b-09d45b17cad7,72f8ae88-58c9-40b4-863a-1c7bc6549a8b,52c10f07-6653-470d-9fee-14b0bb111c2a,d309898b-3925-494f-a30c-689222d3fcce,dbacb5dc-c8a3-439d-b407-13ffd570b9ef,27400130-8127-4f54-b14f-e26f20ecae14,14e83edc-5a54-44f5-816e-c96c61b5d911,9c183088-e498-4183-af41-b29bd32d94b6,66c88197-8281-4eb4-ae2e-4a89ae8419ed,1018b255-0889-492c-b5dd-31a50cb3db4d,5d99a60e-126e-4c40-b5ce-439f920de090,9a0e7727-b011-458f-832a-61108b2fe381,70589012-899c-401d-85a1-13fabce26aab,e5631d3e-70c3-4083-ac17-46f9467c6dd5,e447d5bb-8d42-4be4-b91d-b8d185cf81a6,18b3841b-b5b1-4971-93d0-d36ac20c4565,fee237ef-75e8-4ada-b15f-6d1a92633f33,16c58ef5-3b19-4ec2-ba9c-aefac3d08a66,7a663f5e-2619-4a2d-a7df-7250263f47d2,e2b4a441-21b5-4d03-816b-09d45b17cad7&attribute=card_status:needs_card', ]); expect(setSubmittingMock.mock.calls[1][0]).toEqual(false); expect(papaparseMock).not.toHaveBeenCalled(); @@ -216,6 +232,7 @@ describe('components/DownloadClientData/utils/submitForm', () => { }); it('calls API correctly if card status is empty', async () => { + fetch.mockOnce(JSON.stringify(fixtures.locationHierarchy)); fetch.mockResponse(JSON.stringify([fixtures.mother, fixtures.child1, fixtures.child2])); submitForm( @@ -233,16 +250,9 @@ describe('components/DownloadClientData/utils/submitForm', () => { await flushPromises(); }); expect(setSubmittingMock.mock.calls[0][0]).toEqual(true); - expect(fetch.mock.calls[0]).toEqual([ - `https://unicef-tunisia-stage.smartregister.org/opensrp/rest/client/search?locationIds=${clientLocation}`, - { - headers: { - accept: 'application/json', - authorization: 'Bearer hunter2', - 'content-type': 'application/json;charset=UTF-8', - }, - method: 'GET', - }, + expect(fetch.mock.calls.map((res) => res[0])).toEqual([ + 'https://unicef-tunisia-stage.smartregister.org/opensrp/rest/location/hierarchy/e2b4a441-21b5-4d03-816b-09d45b17cad7', + 'https://unicef-tunisia-stage.smartregister.org/opensrp/rest/client/search?locationIds=325b9549-80fa-4dd0-9cf8-f0538cbebb18,e2b4a441-21b5-4d03-816b-09d45b17cad7,72f8ae88-58c9-40b4-863a-1c7bc6549a8b,52c10f07-6653-470d-9fee-14b0bb111c2a,d309898b-3925-494f-a30c-689222d3fcce,dbacb5dc-c8a3-439d-b407-13ffd570b9ef,27400130-8127-4f54-b14f-e26f20ecae14,14e83edc-5a54-44f5-816e-c96c61b5d911,9c183088-e498-4183-af41-b29bd32d94b6,66c88197-8281-4eb4-ae2e-4a89ae8419ed,1018b255-0889-492c-b5dd-31a50cb3db4d,5d99a60e-126e-4c40-b5ce-439f920de090,9a0e7727-b011-458f-832a-61108b2fe381,70589012-899c-401d-85a1-13fabce26aab,e5631d3e-70c3-4083-ac17-46f9467c6dd5,e447d5bb-8d42-4be4-b91d-b8d185cf81a6,18b3841b-b5b1-4971-93d0-d36ac20c4565,fee237ef-75e8-4ada-b15f-6d1a92633f33,16c58ef5-3b19-4ec2-ba9c-aefac3d08a66,7a663f5e-2619-4a2d-a7df-7250263f47d2,e2b4a441-21b5-4d03-816b-09d45b17cad7', ]); expect(setSubmittingMock.mock.calls[1][0]).toEqual(false); expect(papaparseMock).toBeCalledWith([fixtures.child1CsvEntry, fixtures.child2CsvEntry], { From e9676a5a5a1b6f066d45ad3b735982f958387ffa Mon Sep 17 00:00:00 2001 From: Macharia Muguku Date: Thu, 27 Jan 2022 15:24:21 +0300 Subject: [PATCH 3/6] fix lint warnings - prettier, catch promises --- .../components/DownloadClientData/index.tsx | 2 +- .../DownloadClientData/tests/utils.test.tsx | 25 ++++++++++++------- .../components/DownloadClientData/utils.tsx | 5 ++-- 3 files changed, 20 insertions(+), 12 deletions(-) diff --git a/packages/card-support/src/components/DownloadClientData/index.tsx b/packages/card-support/src/components/DownloadClientData/index.tsx index 14791324c..b968c7fd3 100644 --- a/packages/card-support/src/components/DownloadClientData/index.tsx +++ b/packages/card-support/src/components/DownloadClientData/index.tsx @@ -167,7 +167,7 @@ const DownloadClientData: React.FC = (props: DownloadCl opensrpServiceClass, locationHierarchies, setSubmitting - ); + ).catch(() => sendErrorNotification(lang.ERROR_OCCURRED)); }} > diff --git a/packages/card-support/src/components/DownloadClientData/tests/utils.test.tsx b/packages/card-support/src/components/DownloadClientData/tests/utils.test.tsx index 23e82fdf7..0bab68491 100644 --- a/packages/card-support/src/components/DownloadClientData/tests/utils.test.tsx +++ b/packages/card-support/src/components/DownloadClientData/tests/utils.test.tsx @@ -155,7 +155,7 @@ describe('components/DownloadClientData/utils/submitForm', () => { OpenSRPService, fixtures.locations, setSubmittingMock - ); + ).catch(() => {}); await act(async () => { await flushPromises(); @@ -190,7 +190,8 @@ describe('components/DownloadClientData/utils/submitForm', () => { OpenSRPService, fixtures.locations, setSubmittingMock - ); + ).catch(() => {}); + await act(async () => { await flushPromises(); }); @@ -217,7 +218,8 @@ describe('components/DownloadClientData/utils/submitForm', () => { OpenSRPService, fixtures.locations, setSubmittingMock - ); + ).catch(() => {}); + await act(async () => { await flushPromises(); }); @@ -245,7 +247,8 @@ describe('components/DownloadClientData/utils/submitForm', () => { OpenSRPService, fixtures.locations, setSubmittingMock - ); + ).catch(() => {}); + await act(async () => { await flushPromises(); }); @@ -272,7 +275,8 @@ describe('components/DownloadClientData/utils/submitForm', () => { OpenSRPService, fixtures.locations, setSubmittingMock - ); + ).catch(() => {}); + await act(async () => { await flushPromises(); }); @@ -295,7 +299,7 @@ describe('components/DownloadClientData/utils/submitForm', () => { OpenSRPService, fixtures.locations, setSubmittingMock - ); + ).catch(() => {}); await act(async () => { await flushPromises(); @@ -308,6 +312,7 @@ describe('components/DownloadClientData/utils/submitForm', () => { it('filters correctly if registration date does not meet range', async () => { fetch.mockResponse(JSON.stringify([fixtures.mother, fixtures.child1, fixtures.child2])); + submitForm( { ...values, @@ -318,7 +323,7 @@ describe('components/DownloadClientData/utils/submitForm', () => { OpenSRPService, fixtures.locations, setSubmittingMock - ); + ).catch(() => {}); await act(async () => { await flushPromises(); @@ -342,7 +347,8 @@ describe('components/DownloadClientData/utils/submitForm', () => { OpenSRPService, fixtures.locations, setSubmittingMock - ); + ).catch(() => {}); + await act(async () => { await flushPromises(); }); @@ -364,7 +370,8 @@ describe('components/DownloadClientData/utils/submitForm', () => { OpenSRPService, fixtures.locations, setSubmittingMock - ); + ).catch(() => {}); + await act(async () => { await flushPromises(); }); diff --git a/packages/card-support/src/components/DownloadClientData/utils.tsx b/packages/card-support/src/components/DownloadClientData/utils.tsx index 19717abba..e71c6ad5f 100644 --- a/packages/card-support/src/components/DownloadClientData/utils.tsx +++ b/packages/card-support/src/components/DownloadClientData/utils.tsx @@ -92,8 +92,9 @@ export const submitForm = async ( ...flatNestedLocationIds, clientLocationId, ]; - const stringifiedFlatNestedLocationIdsWithClientLocationId = - flatNestedLocationIdsWithClientLocationId.join(','); + const stringifiedFlatNestedLocationIdsWithClientLocationId = flatNestedLocationIdsWithClientLocationId.join( + ',' + ); return stringifiedFlatNestedLocationIdsWithClientLocationId; } catch (_) { sendErrorNotification(langObj.ERROR_OCCURRED); From ca9c26fbaeab284625f774bc1643883e9b9b1e55 Mon Sep 17 00:00:00 2001 From: Macharia Muguku Date: Thu, 27 Jan 2022 15:37:45 +0300 Subject: [PATCH 4/6] disable eslint no empty arrow function rule --- .../src/components/DownloadClientData/tests/utils.test.tsx | 1 + 1 file changed, 1 insertion(+) diff --git a/packages/card-support/src/components/DownloadClientData/tests/utils.test.tsx b/packages/card-support/src/components/DownloadClientData/tests/utils.test.tsx index 0bab68491..06eb76ab2 100644 --- a/packages/card-support/src/components/DownloadClientData/tests/utils.test.tsx +++ b/packages/card-support/src/components/DownloadClientData/tests/utils.test.tsx @@ -18,6 +18,7 @@ import * as notifications from '@opensrp/notifications'; import lang from '../../../lang'; /* eslint-disable @typescript-eslint/no-explicit-any */ /* eslint-disable @typescript-eslint/camelcase */ +/* eslint-disable @typescript-eslint/no-empty-function */ jest.mock('@opensrp/notifications', () => ({ __esModule: true, From 7457801a80ce51de3b647516ee0e8a0b5fecb2af Mon Sep 17 00:00:00 2001 From: Macharia Muguku Date: Thu, 27 Jan 2022 15:57:19 +0300 Subject: [PATCH 5/6] update snapshot --- .../tests/__snapshots__/index.test.tsx.snap | 4 ++++ 1 file changed, 4 insertions(+) diff --git a/packages/card-support/src/components/DownloadClientData/tests/__snapshots__/index.test.tsx.snap b/packages/card-support/src/components/DownloadClientData/tests/__snapshots__/index.test.tsx.snap index e08f3c31a..b018a8231 100644 --- a/packages/card-support/src/components/DownloadClientData/tests/__snapshots__/index.test.tsx.snap +++ b/packages/card-support/src/components/DownloadClientData/tests/__snapshots__/index.test.tsx.snap @@ -69,6 +69,10 @@ Object { title="All Locations" value="" /> + Date: Thu, 27 Jan 2022 16:12:48 +0300 Subject: [PATCH 6/6] update tests - check that catch runs on reject promise --- .../DownloadClientData/tests/utils.test.tsx | 26 +++++++++++++++++++ 1 file changed, 26 insertions(+) diff --git a/packages/card-support/src/components/DownloadClientData/tests/utils.test.tsx b/packages/card-support/src/components/DownloadClientData/tests/utils.test.tsx index 06eb76ab2..ab997d9d1 100644 --- a/packages/card-support/src/components/DownloadClientData/tests/utils.test.tsx +++ b/packages/card-support/src/components/DownloadClientData/tests/utils.test.tsx @@ -16,6 +16,7 @@ import { act } from 'react-dom/test-utils'; import flushPromises from 'flush-promises'; import * as notifications from '@opensrp/notifications'; import lang from '../../../lang'; +import * as functions from '../utils'; /* eslint-disable @typescript-eslint/no-explicit-any */ /* eslint-disable @typescript-eslint/camelcase */ /* eslint-disable @typescript-eslint/no-empty-function */ @@ -206,6 +207,31 @@ describe('components/DownloadClientData/utils/submitForm', () => { expect(notificationErrorMock).toHaveBeenCalledWith(lang.ERROR_OCCURRED); }); + it('handles error if submit form fails', async () => { + fetch.mockReject(() => Promise.reject('API is down')); + fetch.mockOnce(JSON.stringify(fixtures.locationHierarchy)); + + const mockRejectFn = jest.fn(); + jest.spyOn(functions, 'submitForm').mockRejectedValueOnce(() => Promise.reject('API is down')); + + submitForm( + values, + accessToken, + opensrpBaseURL, + OpenSRPService, + fixtures.locations, + setSubmittingMock + ).catch(() => { + mockRejectFn(); + }); + + await act(async () => { + await flushPromises(); + }); + + expect(mockRejectFn).toHaveBeenCalled(); + }); + it('handles error if submission fails', async () => { fetch.mockOnce(JSON.stringify(fixtures.locationHierarchy)); fetch.mockReject(() => Promise.reject('API is down'));