private void createIvrAndSmsStatisticReport( CallDetailRecord initialRecord) { // NO CHECKSTYLE CyclomaticComplexity DateTimeFormatter motechTimestampFormatter = DateTimeFormat.forPattern(EbodacConstants.IVR_CALL_DETAIL_RECORD_TIME_FORMAT); DateTimeFormatter votoTimestampFormatter = DateTimeFormat.forPattern(EbodacConstants.VOTO_TIMESTAMP_FORMAT); String providerCallId = initialRecord.getProviderCallId(); Map<String, String> providerExtraData = initialRecord.getProviderExtraData(); if (StringUtils.isBlank(providerCallId)) { throw new EbodacReportException( "Cannot generate report for Call Detail Record with Motech Call Id: %s, because Provider Call Id is empty", "", initialRecord.getMotechCallId()); } if (providerExtraData == null || providerExtraData.isEmpty()) { throw new EbodacReportException( "Cannot generate report for Call Detail Record with Motech Call Id: %s, because Provider Extra Data Map is empty", "", initialRecord.getMotechCallId()); } String subjectIds = providerExtraData.get(EbodacConstants.SUBJECT_IDS); List<Subject> subjects = new ArrayList<>(); if (StringUtils.isBlank(subjectIds)) { throw new EbodacReportException( "Cannot generate report for Call Detail Record with Motech Call Id: %s, because no ParticipantId found In Provider Extra Data Map", "", initialRecord.getMotechCallId()); } for (String subjectId : subjectIds.split(",")) { Subject subject = subjectService.findSubjectBySubjectId(subjectId.trim()); if (subject != null) { subjects.add(subject); } else { LOGGER.warn( "Cannot generate report for Provider Call Id: {} and ParticipantId: {}, because no Participant with this Id found", providerCallId, subjectId); } } if (subjects.isEmpty()) { throw new EbodacReportException( "Cannot generate report for Call Detail Record with Motech Call Id: %s, because No Participants found with Ids: %s", "", initialRecord.getMotechCallId(), subjectIds); } List<CallDetailRecord> callDetailRecords = callDetailRecordDataService.findByExactProviderCallId( providerCallId, QueryParams.ascOrder(EbodacConstants.IVR_CALL_DETAIL_RECORD_MOTECH_TIMESTAMP_FIELD)); List<CallDetailRecord> failed = new ArrayList<>(); List<CallDetailRecord> finished = new ArrayList<>(); boolean sms = false; boolean smsFailed = false; String messageId = providerExtraData.get(EbodacConstants.MESSAGE_ID); DateTime sendDate = DateTime.parse(initialRecord.getMotechTimestamp(), motechTimestampFormatter); int attempts = 0; DateTime receivedDate = null; DateTime smsReceivedDate = null; double expectedDuration = 0; double timeListenedTo = 0; double messagePercentListened = 0; for (CallDetailRecord callDetailRecord : callDetailRecords) { if (callDetailRecord.getCallStatus() == null) { continue; } if (callDetailRecord .getCallStatus() .contains(EbodacConstants.IVR_CALL_DETAIL_RECORD_STATUS_SUBMITTED)) { sms = true; } else if (callDetailRecord .getCallStatus() .contains(EbodacConstants.IVR_CALL_DETAIL_RECORD_STATUS_FINISHED)) { finished.add(callDetailRecord); } else if (callDetailRecord .getCallStatus() .contains(EbodacConstants.IVR_CALL_DETAIL_RECORD_STATUS_FAILED)) { failed.add(callDetailRecord); } } Integer recordsCount = failed.size() + finished.size(); CallDetailRecord callRecord; if (sms) { if (failed.isEmpty()) { throw new EbodacReportException( "Cannot generate report for Call Detail Record with Provider Call Id: %s for Providers with Ids %s, because SMS was sent but no failed record found for the Call", "", providerCallId, subjectIds); } if (recordsCount > 2) { throw new EbodacReportException( "Cannot generate report for Call Detail Record with Provider Call Id: %s for Providers with Ids %s, because there is too much records with failed/finished status (%s)", "", providerCallId, subjectIds, recordsCount.toString()); } if (failed.size() == 2) { smsFailed = true; LOGGER.warn( "Failed to sent SMS for Call Detail Record with Provider Call Id: {} for Providers with Ids {}", providerCallId, subjectIds); } else if (finished.isEmpty()) { LOGGER.warn( "SMS is sent but not yet received for Call Detail Record with Provider Call Id: {} for Providers with Ids {}", providerCallId, subjectIds); Config config = configService.getConfig(); config.getIvrAndSmsStatisticReportsToUpdate().add(initialRecord.getMotechCallId()); configService.updateConfig(config); } else { String providerTimestamp = finished .get(0) .getProviderExtraData() .get(EbodacConstants.IVR_CALL_DETAIL_RECORD_END_TIMESTAMP); if (StringUtils.isBlank(providerTimestamp)) { throw new EbodacReportException( "Cannot generate report for Call Detail Record with Provider Call Id: %s for Providers with Ids %s, because end_timestamp for SMS Record not found", "", providerCallId, subjectIds); } smsReceivedDate = DateTime.parse(providerTimestamp, votoTimestampFormatter); } callRecord = failed.get(0); } else if (recordsCount == 2 && failed.size() == 2) { callRecord = failed.get(0); smsFailed = true; LOGGER.warn( "Failed to sent SMS for Call Detail Record with Provider Call Id: {} for Providers with Ids {}", providerCallId, subjectIds); } else { if (recordsCount > 1) { throw new EbodacReportException( "Cannot generate report for Call Detail Record with Provider Call Id: %s for Providers with Ids %s, because there is too much records with failed/finished status (%s)", "", providerCallId, subjectIds, recordsCount.toString()); } if (finished.isEmpty()) { throw new EbodacReportException( "Cannot generate report for Call Detail Record with Provider Call Id: %s for Providers with Ids %s, because no SMS was sent but there is no record with finished status", "", providerCallId, subjectIds); } callRecord = finished.get(0); String providerTimestamp = callRecord .getProviderExtraData() .get(EbodacConstants.IVR_CALL_DETAIL_RECORD_START_TIMESTAMP); if (StringUtils.isBlank(providerTimestamp)) { throw new EbodacReportException( "Cannot generate report for Call Detail Record with Provider Call Id: %s for Providers with Ids %s, because start_timestamp for Call Record not found", "", providerCallId, subjectIds); } receivedDate = DateTime.parse(providerTimestamp, votoTimestampFormatter); if (StringUtils.isNotBlank(callRecord.getCallDuration())) { timeListenedTo = Double.parseDouble(callRecord.getCallDuration()); if (StringUtils.isNotBlank(callRecord.getMessagePercentListened())) { messagePercentListened = Double.parseDouble(callRecord.getMessagePercentListened()); String messageSecondsCompleted = callRecord .getProviderExtraData() .get(EbodacConstants.IVR_CALL_DETAIL_RECORD_MESSAGE_SECOND_COMPLETED); if (StringUtils.isNotBlank(messageSecondsCompleted)) { expectedDuration = Double.parseDouble(messageSecondsCompleted) * HUNDRED_PERCENT / messagePercentListened; } } } } String attemptsString = callRecord .getProviderExtraData() .get(EbodacConstants.IVR_CALL_DETAIL_RECORD_NUMBER_OF_ATTEMPTS); if (StringUtils.isNotBlank(attemptsString)) { attempts = Integer.parseInt(attemptsString); } for (Subject subject : subjects) { IvrAndSmsStatisticReport ivrAndSmsStatisticReport = ivrAndSmsStatisticReportDataService.findByProviderCallIdAndSubjectId( providerCallId, subject.getSubjectId()); if (ivrAndSmsStatisticReport == null) { ivrAndSmsStatisticReport = new IvrAndSmsStatisticReport( providerCallId, subject, messageId, sendDate, expectedDuration, timeListenedTo, messagePercentListened, receivedDate, attempts, sms, smsFailed, smsReceivedDate); ivrAndSmsStatisticReportDataService.create(ivrAndSmsStatisticReport); } else { ivrAndSmsStatisticReport.updateReportData( providerCallId, subject, messageId, sendDate, expectedDuration, timeListenedTo, messagePercentListened, receivedDate, attempts, sms, smsFailed, smsReceivedDate); ivrAndSmsStatisticReportDataService.update(ivrAndSmsStatisticReport); } } }
private void resetTestFields() { firstSubject = new Subject( "1000000161", "Michal", "Abacki", "Cabacki", "729402018364", "address", Language.English, "community", "B05-SL10001"); secondSubject = new Subject( "1000000162", "Rafal", "Dabacki", "Ebacki", "44443333222", "address1", Language.Susu, "community", "B05-SL10001"); firstSubject.setDateOfBirth(LocalDate.parse("1967-09-17", formatter)); firstSubject.setGender(Gender.Male); firstSubject.setPrimerVaccinationDate(LocalDate.parse("2014-10-17", formatter)); firstSubject.setBoosterVaccinationDate(LocalDate.parse("2014-10-20", formatter)); secondSubject.setDateOfBirth(LocalDate.parse("2005-08-04", formatter)); secondSubject.setGender(Gender.Male); secondSubject.setPrimerVaccinationDate(LocalDate.parse("2014-10-17", formatter)); secondSubject.setBoosterVaccinationDate(LocalDate.parse("2014-10-20", formatter)); testVisits.add( VisitUtils.createVisit( firstSubject, VisitType.SCREENING, LocalDate.parse("2014-10-17", formatter), LocalDate.parse("2014-10-17", formatter), "owner")); testVisits.add( VisitUtils.createVisit( firstSubject, VisitType.PRIME_VACCINATION_FOLLOW_UP_VISIT, LocalDate.parse("2014-10-19", formatter), LocalDate.parse("2014-10-19", formatter), "owner")); testVisits.add( VisitUtils.createVisit( secondSubject, VisitType.SCREENING, LocalDate.parse("2014-10-19", formatter), LocalDate.parse("2014-10-19", formatter), "owner")); testVisits.add( VisitUtils.createVisit( secondSubject, VisitType.PRIME_VACCINATION_FOLLOW_UP_VISIT, LocalDate.parse("2014-10-21", formatter), LocalDate.parse("2014-10-21", formatter), "owner")); testVisits.add( VisitUtils.createVisit( firstSubject, VisitType.BOOST_VACCINATION_DAY, LocalDate.parse("2014-10-17", formatter), LocalDate.parse("2014-10-17", formatter), "owner")); }
private void generateOrUpdatePrimerVaccinationReport(List<Subject> subjects, LocalDate date) { LocalDate age6 = date.minusYears(SIX_YEARS); LocalDate age12 = date.minusYears(TWELVE_YEARS); LocalDate age18 = date.minusYears(EIGHTEEN_YEARS); int childrenFrom1To5 = 0; int childrenFrom6To11 = 0; int childrenFrom12To17 = 0; int adultMales = 0; int adultFemales = 0; int adultUndifferentiated = 0; int adultUnidentified = 0; for (Subject subject : subjects) { if (subject.getDateOfBirth() == null) { LOGGER.warn("Subject with id: {} has no birth date", subject.getSubjectId()); } else if (subject.getDateOfBirth().isAfter(age6)) { childrenFrom1To5++; } else if (subject.getDateOfBirth().isAfter(age12)) { childrenFrom6To11++; } else if (subject.getDateOfBirth().isAfter(age18)) { childrenFrom12To17++; } else if (Gender.Male.equals(subject.getGender())) { adultMales++; } else if (Gender.Female.equals(subject.getGender())) { adultFemales++; } else if (Gender.Undifferentiated.equals(subject.getGender())) { adultUndifferentiated++; } else { adultUnidentified++; } } int peopleVaccinated = childrenFrom1To5 + childrenFrom6To11 + childrenFrom12To17 + adultMales + adultFemales; ReportPrimerVaccination existingReport = primerVaccinationDataService.findByDate(date); if (existingReport != null) { existingReport.updateReportData( adultMales, adultFemales, childrenFrom1To5, childrenFrom6To11, childrenFrom12To17, adultUnidentified, adultUndifferentiated, peopleVaccinated); primerVaccinationDataService.update(existingReport); LOGGER.debug( "Primer Vaccination Daily Report for date: {} updated", date.toString(DateTimeFormat.forPattern(EbodacConstants.REPORT_DATE_FORMAT))); } else { ReportPrimerVaccination reportPrimerVaccination = new ReportPrimerVaccination( date, adultMales, adultFemales, childrenFrom1To5, childrenFrom6To11, childrenFrom12To17, adultUnidentified, adultUndifferentiated, peopleVaccinated); primerVaccinationDataService.create(reportPrimerVaccination); LOGGER.debug( "Primer Vaccination Daily Report for date: {} created", date.toString(DateTimeFormat.forPattern(EbodacConstants.REPORT_DATE_FORMAT))); } }