NTP-58799 | Persist original image (#1157)
This commit is contained in:
@@ -270,7 +270,6 @@ public class PhotoModule extends ReactContextBaseJavaModule {
|
||||
String longitude = attributes.getString("longitude");
|
||||
|
||||
exif.setAttribute(ExifInterface.TAG_IMAGE_DESCRIPTION, json.toString());
|
||||
exif.setAttribute(ExifInterface.TAG_ARTIST, "Aman Chaturvedi (1932)");
|
||||
String currentDateTime = getCurrentFormattedDateTime();
|
||||
|
||||
exif.setAttribute(ExifInterface.TAG_DATETIME, currentDateTime);
|
||||
|
||||
@@ -10,6 +10,8 @@ import { type IDocument, removeDocumentByQuestionKey } from '../reducer/feedback
|
||||
import { addClickstreamEvent } from '@services/clickstreamEventService';
|
||||
import { CLICKSTREAM_EVENT_NAMES } from '@common/Constants';
|
||||
import { PAST_FEEDBACK_PAGE_SIZE } from '@screens/caseDetails/feedback/pastFeedbackCommon';
|
||||
import RNBlobUtil from 'react-native-blob-util';
|
||||
import logger from '@components/utlis/logger';
|
||||
|
||||
export const getRepaymentsData = (loanAccountNumber: string, caseId: string, caseBusinessVertical: string) => (dispatch: AppDispatch) => {
|
||||
dispatch(setRepaymentsLoading({ loanAccountNumber, isLoading: true }));
|
||||
@@ -119,54 +121,93 @@ export const getFeedbackHistory = (loanAccountNumber: string) => (dispatch: AppD
|
||||
|
||||
export const uploadImages =
|
||||
(caseKey: string, documents: Record<string, IDocument>, interactionReferenceId: string) =>
|
||||
(dispatch: AppDispatch) => {
|
||||
async (dispatch: AppDispatch) => {
|
||||
if (!documents || !interactionReferenceId) {
|
||||
return;
|
||||
}
|
||||
_map(documents, (questionKey, index) => {
|
||||
for (const questionKey of Object.keys(documents)) {
|
||||
const fileDoc = documents[questionKey];
|
||||
if (!fileDoc) {
|
||||
return;
|
||||
if (!fileDoc || !fileDoc.fileUri) {
|
||||
continue;
|
||||
}
|
||||
const { fileUri } = fileDoc;
|
||||
const formData = new FormData();
|
||||
formData.append(
|
||||
'originalImageData',
|
||||
JSON.stringify({
|
||||
interactionReferenceId,
|
||||
questionKey,
|
||||
})
|
||||
);
|
||||
formData.append('image', {
|
||||
uri: fileUri,
|
||||
name: `image_${interactionReferenceId}_${index}`,
|
||||
type: 'image/jpeg',
|
||||
} as any);
|
||||
const url = getApiUrl(ApiKeys.UPLOAD_FEEDBACK_IMAGES);
|
||||
axiosInstance
|
||||
.put(url, formData, {
|
||||
headers: {
|
||||
'Content-Type': 'multipart/form-data',
|
||||
donotHandleError: true,
|
||||
const mimeType = 'image/jpeg';
|
||||
try {
|
||||
// Get pre-signed URL
|
||||
const presignRes = await axiosInstance.post(
|
||||
getApiUrl(ApiKeys.GET_PRE_SIGNED_URL_FOR_FEEDBACK_IMAGE),
|
||||
{
|
||||
interactionReferenceId,
|
||||
questionKey,
|
||||
mimeType,
|
||||
},
|
||||
timeout: 5 * MILLISECONDS_IN_A_MINUTE,
|
||||
})
|
||||
.then((res) => {
|
||||
dispatch(removeDocumentByQuestionKey({ caseKey, questionKey }));
|
||||
})
|
||||
.catch((err) => {
|
||||
if (err?.response?.status === API_STATUS_CODE.NOT_FOUND) {
|
||||
dispatch(removeDocumentByQuestionKey({ caseKey, questionKey }));
|
||||
addClickstreamEvent(CLICKSTREAM_EVENT_NAMES.FA_WRONG_QUESTION_KEY, {
|
||||
error: err,
|
||||
questionKey,
|
||||
interactionReferenceId,
|
||||
});
|
||||
{
|
||||
headers: { doNotHandleError: true },
|
||||
}
|
||||
addClickstreamEvent(CLICKSTREAM_EVENT_NAMES.FA_PERSIST_ORIGINAL_IMAGE_FAILURE, {
|
||||
payload: formData,
|
||||
});
|
||||
logError(err as Error, 'Error uploading image to document service');
|
||||
);
|
||||
if (!presignRes?.data?.presignedUrl || !presignRes?.data?.id) {
|
||||
throw new Error('Failed to get presigned URL');
|
||||
}
|
||||
|
||||
addClickstreamEvent(CLICKSTREAM_EVENT_NAMES.FA_PERSIST_ORIGINAL_IMAGE_PRESIGNED_SUCCESS, {
|
||||
payload: {
|
||||
questionKey,
|
||||
interactionReferenceId,
|
||||
},
|
||||
});
|
||||
});
|
||||
|
||||
// Upload image to pre-signed URL
|
||||
const fileStats = await RNBlobUtil.fs.stat(fileDoc.fileUri);
|
||||
await RNBlobUtil.fetch(
|
||||
'PUT',
|
||||
presignRes?.data?.presignedUrl,
|
||||
{
|
||||
'Content-Type': mimeType,
|
||||
},
|
||||
RNBlobUtil.wrap(fileStats.path)
|
||||
);
|
||||
|
||||
addClickstreamEvent(CLICKSTREAM_EVENT_NAMES.FA_PERSIST_ORIGINAL_IMAGE_S3_SUCCESS, {
|
||||
payload: {
|
||||
questionKey,
|
||||
interactionReferenceId,
|
||||
},
|
||||
});
|
||||
|
||||
// Acknowledge
|
||||
await axiosInstance.post(
|
||||
getApiUrl(ApiKeys.FEEDBACK_ORIGINAL_IMAGE_ACK),
|
||||
{},
|
||||
{
|
||||
params: { id: presignRes?.data?.id },
|
||||
headers: { doNotHandleError: true },
|
||||
}
|
||||
);
|
||||
addClickstreamEvent(CLICKSTREAM_EVENT_NAMES.FA_PERSIST_ORIGINAL_IMAGE_ACKNOWLEDGE_SUCCESS, {
|
||||
payload: {
|
||||
questionKey,
|
||||
interactionReferenceId,
|
||||
},
|
||||
});
|
||||
|
||||
// Remove document from redux
|
||||
dispatch(removeDocumentByQuestionKey({ caseKey, questionKey }));
|
||||
} catch (err) {
|
||||
logger({
|
||||
msg: `Image upload failed`,
|
||||
type: 'error',
|
||||
extras: {
|
||||
error: err,
|
||||
questionKey,
|
||||
interactionReferenceId,
|
||||
},
|
||||
});
|
||||
addClickstreamEvent(CLICKSTREAM_EVENT_NAMES.FA_PERSIST_ORIGINAL_IMAGE_FAILURE, {
|
||||
payload: {
|
||||
questionKey,
|
||||
interactionReferenceId,
|
||||
},
|
||||
});
|
||||
continue;
|
||||
}
|
||||
}
|
||||
};
|
||||
|
||||
@@ -1433,6 +1433,19 @@ export const CLICKSTREAM_EVENT_NAMES = {
|
||||
description: 'Failed to persist original image',
|
||||
},
|
||||
|
||||
FA_PERSIST_ORIGINAL_IMAGE_PRESIGNED_SUCCESS: {
|
||||
name: 'FA_PERSIST_ORIGINAL_IMAGE_PRESIGNED_SUCCESS',
|
||||
description: 'Successfully presigned generated for original image',
|
||||
},
|
||||
FA_PERSIST_ORIGINAL_IMAGE_S3_SUCCESS: {
|
||||
name: 'FA_PERSIST_ORIGINAL_IMAGE_S3_SUCCESS',
|
||||
description: 'Successfully persisted original image to S3',
|
||||
},
|
||||
FA_PERSIST_ORIGINAL_IMAGE_ACKNOWLEDGE_SUCCESS: {
|
||||
name: 'FA_PERSIST_ORIGINAL_IMAGE_ACKNOWLEDGE_SUCCESS',
|
||||
description: 'Successfully acknowledged original image',
|
||||
},
|
||||
|
||||
// Filter coachmarks
|
||||
FA_FILTER_COACHMARKS_LOADED: {
|
||||
name: 'FA_FILTER_COACHMARKS_LOADED',
|
||||
|
||||
@@ -120,7 +120,9 @@ export enum ApiKeys {
|
||||
GET_TRAINING_MATERIAL_LIST = 'GET_TRAINING_MATERIAL_LIST',
|
||||
GET_TRAINING_MATERIAL_DETAILS = 'GET_TRAINING_MATERIAL_DETAILS',
|
||||
SELF_CALL_ACK= '/api/v1/self-call',
|
||||
GET_CASES_GEOLOCATION_DISTANCE_FROM_AGENT_LOCATION = "GET_CASES_GEOLOCATION_DISTANCE_FROM_AGENT_LOCATION"
|
||||
GET_CASES_GEOLOCATION_DISTANCE_FROM_AGENT_LOCATION = "GET_CASES_GEOLOCATION_DISTANCE_FROM_AGENT_LOCATION",
|
||||
GET_PRE_SIGNED_URL_FOR_FEEDBACK_IMAGE = 'GET_PRE_SIGNED_URL_FOR_FEEDBACK_IMAGE',
|
||||
FEEDBACK_ORIGINAL_IMAGE_ACK = 'FEEDBACK_ORIGINAL_IMAGE_ACK',
|
||||
}
|
||||
|
||||
export const API_URLS: Record<ApiKeys, string> = {} as Record<ApiKeys, string>;
|
||||
@@ -230,6 +232,8 @@ API_URLS[ApiKeys.SELF_CALL_ACK] = '/sync-data/self-call-metadata';
|
||||
API_URLS[ApiKeys.GET_TOP_ADDRESSES] = '/collection-cases/unified-locations';
|
||||
API_URLS[ApiKeys.GET_FEEDBACK_ADDRESSES] = '/collection-cases/unified-locations/lite';
|
||||
API_URLS[ApiKeys.GET_CASES_GEOLOCATION_DISTANCE_FROM_AGENT_LOCATION] = '/geolocation-distance/single-source'
|
||||
API_URLS[ApiKeys.GET_PRE_SIGNED_URL_FOR_FEEDBACK_IMAGE] = '/file-upload/presigned-url';
|
||||
API_URLS[ApiKeys.FEEDBACK_ORIGINAL_IMAGE_ACK] = '/file-upload/acknowledge';
|
||||
|
||||
export const API_STATUS_CODE = {
|
||||
OK: 200,
|
||||
|
||||
Reference in New Issue
Block a user