/* * This program is part of the OpenLMIS logistics management information system platform software. * Copyright © 2013 VillageReach * * This program is free software: you can redistribute it and/or modify it under the terms of the GNU Affero General Public License as published by the Free Software Foundation, either version 3 of the License, or (at your option) any later version. *   * This program is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU Affero General Public License for more details. * You should have received a copy of the GNU Affero General Public License along with this program.  If not, see http://www.gnu.org/licenses.  For additional information contact info@OpenLMIS.org.  */ package org.openlmis.web.view.pdf.requisition; import com.itextpdf.text.DocumentException; import com.itextpdf.text.Paragraph; import com.itextpdf.text.pdf.PdfPCell; import com.itextpdf.text.pdf.PdfPRow; import com.itextpdf.text.pdf.PdfPTable; import org.junit.Before; import org.junit.Test; import org.junit.experimental.categories.Category; import org.junit.runner.RunWith; import org.mockito.Mock; import org.mockito.runners.MockitoJUnitRunner; import org.openlmis.core.builder.FacilityBuilder; import org.openlmis.core.domain.Facility; import org.openlmis.core.domain.Program; import org.openlmis.core.domain.User; import org.openlmis.core.service.ConfigurationSettingService; import org.openlmis.core.service.MessageService; import org.openlmis.db.categories.UnitTests; import org.openlmis.rnr.builder.RnrLineItemBuilder; import org.openlmis.rnr.domain.*; import org.openlmis.web.controller.RequisitionController; import java.math.BigDecimal; import java.util.*; import static com.natpryce.makeiteasy.MakeItEasy.*; import static java.util.Arrays.asList; import static org.hamcrest.CoreMatchers.is; import static org.junit.Assert.assertThat; import static org.mockito.Mockito.*; import static org.openlmis.core.builder.UserBuilder.*; import static org.openlmis.rnr.builder.RegimenColumnBuilder.*; import static org.openlmis.rnr.builder.RequisitionBuilder.*; import static org.openlmis.rnr.builder.RnrTemplateBuilder.defaultRnrTemplate; import static org.openlmis.rnr.domain.RnrStatus.*; import static org.openlmis.web.view.pdf.requisition.RequisitionPdfModel.DATE_FORMAT; @Category(UnitTests.class) @RunWith(MockitoJUnitRunner.class) public class RequisitionPdfModelTest { @Mock MessageService messageService; @Mock private ConfigurationSettingService configService; private Map<String, Object> model; private Rnr requisition; private RequisitionPdfModel requisitionPdfModel; private List<LossesAndAdjustmentsType> lossesAndAdjustmentsList; private Date currentDate; private Date authorizedDate; @Before public void setUp() throws Exception { Facility f1 = make(a(FacilityBuilder.defaultFacility, with(FacilityBuilder.name, "F1"))); requisition = spy(make(a(rnrWithRegimens, with(facility, f1), with(emergency, Boolean.TRUE)))); model = new HashMap<>(); model.put(RequisitionController.CURRENCY, "$"); model.put(RequisitionController.RNR, requisition); List<? extends Column> rnrTemplate = make(a(defaultRnrTemplate)).getColumns(); RegimenColumn regimenColumn1 = make(a(defaultRegimenColumn, with(name, "name"), with(label, "name"))); RegimenColumn regimenColumn2 = make(a(defaultRegimenColumn, with(name, "code"), with(label, "code"))); RegimenColumn regimenColumn3 = make(a(defaultRegimenColumn)); RegimenColumn regimenColumn4 = make(a(defaultRegimenColumn, with(name, "patientsToInitiateTreatment"), with(label, "initiate treatment"))); RegimenColumn regimenColumn5 = make(a(defaultRegimenColumn, with(name, "patientsStoppedTreatment"), with(label, "stopped treatment"))); RegimenColumn regimenColumn6 = make(a(defaultRegimenColumn, with(name, "remarks"), with(label, "remarks"))); List<RegimenColumn> regimenColumnList = Arrays.asList(regimenColumn1, regimenColumn2, regimenColumn3, regimenColumn4, regimenColumn5, regimenColumn6); model.put(RequisitionController.RNR_TEMPLATE, rnrTemplate); model.put(RequisitionController.REGIMEN_TEMPLATE, regimenColumnList); LossesAndAdjustmentsType additive1 = new LossesAndAdjustmentsType("TRANSFER_IN", "TRANSFER IN", true, 1); lossesAndAdjustmentsList = asList(additive1); model.put(RequisitionController.LOSSES_AND_ADJUSTMENT_TYPES, lossesAndAdjustmentsList); currentDate = new Date(); authorizedDate = new Date(); model.put("statusChanges", getRequisitionStatusChanges()); requisitionPdfModel = new RequisitionPdfModel(model, messageService, configService); } private List<RequisitionStatusChange> getRequisitionStatusChanges() { User initiatingUser = make(a(defaultUser, with(firstName, "init-firstName"), with(lastName, "init-lastName"))); User submittingUser = make(a(defaultUser, with(firstName, "submit-firstName"), with(lastName, "submit-lastName"))); User authorizingUser = make(a(defaultUser, with(firstName, "auth-firstName"), with(lastName, "auth-lastName"))); final RequisitionStatusChange initiatedStatusChange = new RequisitionStatusChange(2L, INITIATED, initiatingUser, currentDate); final RequisitionStatusChange submittedStatusChange = new RequisitionStatusChange(2L, SUBMITTED, submittingUser, currentDate); final RequisitionStatusChange authorizedStatusChange = new RequisitionStatusChange(2L, AUTHORIZED, authorizingUser, authorizedDate); return new ArrayList<RequisitionStatusChange>() {{ add(initiatedStatusChange); add(submittedStatusChange); add(authorizedStatusChange); }}; } @Test public void shouldGetHeaderForEmergencyRnr() throws Exception { mockMessageServiceCalls(); when(messageService.message("requisition.type.emergency")).thenReturn("Emergency"); PdfPTable header = requisitionPdfModel.getRequisitionHeader(); assertRowValues(header.getRow(0), "Report and Requisition for: Yellow Fever (Warehouse)"); assertRowValues(header.getRow(1), "Facility: F1", "Operated By: MOH", "Maximum Stock level: 100", "Emergency Order Point: 50.5"); assertRowValues(header.getRow(2), "Facility Code: F10010", "levelName: Arusha", "parentLevelName: Zambia", "Reporting Period: 01/01/2012 - 01/02/2012", "Requisition Type: Emergency"); assertThat(header.getSpacingAfter(), is(RequisitionPdfModel.PARAGRAPH_SPACING)); } @Test public void shouldGetHeaderForRegularRnr() throws Exception { mockMessageServiceCalls(); when(messageService.message("requisition.type.regular")).thenReturn("Regular"); requisition.setEmergency(false); PdfPTable header = requisitionPdfModel.getRequisitionHeader(); assertRowValues(header.getRow(0), "Report and Requisition for: Yellow Fever (Warehouse)"); assertRowValues(header.getRow(1), "Facility: F1", "Operated By: MOH", "Maximum Stock level: 100", "Emergency Order Point: 50.5"); assertRowValues(header.getRow(2), "Facility Code: F10010", "levelName: Arusha", "parentLevelName: Zambia", "Reporting Period: 01/01/2012 - 01/02/2012", "Requisition Type: Regular"); assertThat(header.getSpacingAfter(), is(RequisitionPdfModel.PARAGRAPH_SPACING)); } private void mockMessageServiceCalls() { when(messageService.message("label.requisition")).thenReturn("Report and Requisition for"); when(messageService.message("label.facility")).thenReturn("Facility"); when(messageService.message("create.facility.operatedBy")).thenReturn("Operated By"); when(messageService.message("label.facility.maximumStock")).thenReturn("Maximum Stock level"); when(messageService.message("label.emergency.order.point")).thenReturn("Emergency Order Point"); when(messageService.message("label.facility.reportingPeriod")).thenReturn("Reporting Period"); when(messageService.message("label.requisition.type")).thenReturn("Requisition Type"); when(messageService.message("header.facility.code")).thenReturn("Facility Code"); } @Test public void shouldGetSummary() throws Exception { when(messageService.message("label.summary")).thenReturn("Summary"); when(messageService.message("label.total.cost.full.supply.items")).thenReturn("Total Cost For Full Supply Items"); when(messageService.message("label.total.cost.non.full.supply.items")).thenReturn("Total Cost For Non Full Supply Items"); when(messageService.message("label.total.cost")).thenReturn("Total Cost"); when(messageService.message("label.submitted.by")).thenReturn("Submitted By"); when(messageService.message("label.authorized.by")).thenReturn("Authorized By"); when(messageService.message("label.date")).thenReturn("Date"); when(messageService.message("label.currency.symbol")).thenReturn("$"); PdfPTable summary = requisitionPdfModel.getSummary(); verify(requisition).fillFullSupplyCost(); verify(requisition).fillNonFullSupplyCost(); assertRowValues(summary.getRow(0), "Summary"); assertRowValues(summary.getRow(1), "Total Cost For Full Supply Items", "$8.00"); assertRowValues(summary.getRow(2), "Total Cost For Non Full Supply Items", "$0.00"); assertRowValues(summary.getRow(3), "Total Cost", "$8.00"); assertRowValues(summary.getRow(4), " ", " "); assertRowValues(summary.getRow(5), " ", " "); assertRowValues(summary.getRow(6), "Submitted By: submit-firstName submit-lastName", "Date: " + DATE_FORMAT.format(currentDate.getTime())); assertRowValues(summary.getRow(7), " ", " "); assertRowValues(summary.getRow(8), "Authorized By: auth-firstName auth-lastName", "Date: " + DATE_FORMAT.format(authorizedDate.getTime())); } @Test public void shouldGetFullSupplyHeader() throws Exception { when(messageService.message("label.full.supply.products")).thenReturn("Full supply product(s)"); Paragraph fullSupplyHeader = requisitionPdfModel.getFullSupplyHeader(); assertThat(fullSupplyHeader.getContent(), is("Full supply product(s)")); } @Test public void shouldGetNonFullSupplyHeader() throws Exception { when(messageService.message("label.non.full.supply.products")).thenReturn("Non-Full supply product(s)"); Paragraph nonFullSupplyHeader = requisitionPdfModel.getNonFullSupplyHeader(); assertThat(nonFullSupplyHeader.getContent(), is("Non-Full supply product(s)")); } @Test public void shouldGetRegimenHeader() throws Exception { when(messageService.message("label.regimens")).thenReturn("Regimen(s)"); Paragraph regimenHeader = requisitionPdfModel.getRegimenHeader(); assertThat(regimenHeader.getContent(), is("Regimen(s)")); } @Test public void shouldGetFullSupplyLineItems() throws Exception { PdfPTable fullSupplyTable = requisitionPdfModel.getFullSupplyTable(); assertRowValues(fullSupplyTable.getRow(0), "Requested Quantity", "stockOutDays", "stock in hand", "quantity received", "beginning balance", "losses and adjustment"); assertRowValues(fullSupplyTable.getRow(1), " "); assertRowValues(fullSupplyTable.getRow(2), "C1"); assertRowValues(fullSupplyTable.getRow(3), "6", "3", "4", "3", "10", "1"); assertThat(fullSupplyTable.getRows().size(), is(requisition.getFullSupplyLineItems().size() + 3)); } @Test public void shouldGetNonFullSupplyLineItems() throws Exception { RnrLineItem lineItem = make(a(RnrLineItemBuilder.defaultRnrLineItem)); requisition.add(lineItem, false); PdfPTable nonFullSupplyTable = requisitionPdfModel.getNonFullSupplyTable(); assertRowValues(nonFullSupplyTable.getRow(0), "Requested Quantity"); assertRowValues(nonFullSupplyTable.getRow(1), " "); assertRowValues(nonFullSupplyTable.getRow(2), "C1"); assertRowValues(nonFullSupplyTable.getRow(3), "6"); assertThat(nonFullSupplyTable.getRows().size(), is(requisition.getNonFullSupplyLineItems().size() + 3)); } @Test public void shouldGetRegimenLineItems() throws Exception { PdfPTable regimenTable = requisitionPdfModel.getRegimenTable(); assertRowValues(regimenTable.getRow(0), "name", "code", "patients on treatment", "initiate treatment", "stopped treatment", "remarks"); assertRowValues(regimenTable.getRow(1), " "); assertRowValues(regimenTable.getRow(2), "Category Name"); assertRowValues(regimenTable.getRow(3), "Regimen", "R01", "3", "3", "3", "remarks"); } @Test public void shouldShowAllocatedBudgetIfBudgetAppliesForRegularRnr() throws DocumentException { when(messageService.message("label.summary")).thenReturn("Summary"); when(messageService.message("label.total.cost.full.supply.items")).thenReturn("Total Cost For Full Supply Items"); when(messageService.message("label.total.cost.non.full.supply.items")).thenReturn("Total Cost For Non Full Supply Items"); when(messageService.message("label.total.cost")).thenReturn("Total Cost"); when(messageService.message("label.submitted.by")).thenReturn("Submitted By"); when(messageService.message("label.authorized.by")).thenReturn("Authorized By"); when(messageService.message("label.date")).thenReturn("Date"); when(messageService.message("label.currency.symbol")).thenReturn("$"); when(messageService.message("label.allocated.budget")).thenReturn("Allocated Budget"); when(messageService.message("msg.cost.exceeds.budget")).thenReturn("The total cost exceeds the allocated budget"); Program requisitionProgram = mock(Program.class); when(requisition.getProgram()).thenReturn(requisitionProgram); when(requisition.isEmergency()).thenReturn(false); when(requisitionProgram.getBudgetingApplies()).thenReturn(true); when(requisition.getAllocatedBudget()).thenReturn(new BigDecimal(7)); PdfPTable summary = requisitionPdfModel.getSummary(); assertRowValues(summary.getRow(0), "Summary"); assertRowValues(summary.getRow(1), "Allocated Budget", "$7.00"); assertRowValues(summary.getRow(2), "Total Cost For Full Supply Items", "$8.00"); assertRowValues(summary.getRow(3), "Total Cost For Non Full Supply Items", "$0.00"); assertRowValues(summary.getRow(4), "Total Cost", "$8.00"); assertRowValues(summary.getRow(5), "The total cost exceeds the allocated budget", " "); assertRowValues(summary.getRow(6), " ", " "); assertRowValues(summary.getRow(7), " ", " "); assertRowValues(summary.getRow(8), "Submitted By: submit-firstName submit-lastName", "Date: " + DATE_FORMAT.format(currentDate.getTime())); assertRowValues(summary.getRow(9), " ", " "); assertRowValues(summary.getRow(10), "Authorized By: auth-firstName auth-lastName", "Date: " + DATE_FORMAT.format(authorizedDate.getTime())); } @Test public void shouldShowAllocatedBudgetAsNotAllocatedIfBudgetAppliesForRegularRnrAndNotProvided() throws DocumentException { when(messageService.message("label.summary")).thenReturn("Summary"); when(messageService.message("label.total.cost.full.supply.items")).thenReturn("Total Cost For Full Supply Items"); when(messageService.message("label.total.cost.non.full.supply.items")).thenReturn("Total Cost For Non Full Supply Items"); when(messageService.message("label.total.cost")).thenReturn("Total Cost"); when(messageService.message("label.submitted.by")).thenReturn("Submitted By"); when(messageService.message("label.authorized.by")).thenReturn("Authorized By"); when(messageService.message("label.date")).thenReturn("Date"); when(messageService.message("label.currency.symbol")).thenReturn("$"); when(messageService.message("label.allocated.budget")).thenReturn("Allocated Budget"); when(messageService.message("msg.cost.exceeds.budget")).thenReturn("The total cost exceeds the allocated budget"); when(messageService.message("msg.budget.not.allocated")).thenReturn("Not Allocated"); Program requisitionProgram = mock(Program.class); when(requisition.getProgram()).thenReturn(requisitionProgram); when(requisition.isEmergency()).thenReturn(false); when(requisitionProgram.getBudgetingApplies()).thenReturn(true); when(requisition.getAllocatedBudget()).thenReturn(null); PdfPTable summary = requisitionPdfModel.getSummary(); assertRowValues(summary.getRow(0), "Summary"); assertRowValues(summary.getRow(1), "Allocated Budget", "Not Allocated"); assertRowValues(summary.getRow(2), "Total Cost For Full Supply Items", "$8.00"); assertRowValues(summary.getRow(3), "Total Cost For Non Full Supply Items", "$0.00"); assertRowValues(summary.getRow(4), "Total Cost", "$8.00"); assertRowValues(summary.getRow(5), " ", " "); assertRowValues(summary.getRow(6), " ", " "); assertRowValues(summary.getRow(7), "Submitted By: submit-firstName submit-lastName", "Date: " + DATE_FORMAT.format(currentDate.getTime())); assertRowValues(summary.getRow(8), " ", " "); assertRowValues(summary.getRow(9), "Authorized By: auth-firstName auth-lastName", "Date: " + DATE_FORMAT.format(authorizedDate.getTime())); } private void assertRowValues(PdfPRow row, String... cellTexts) { PdfPCell[] rowCells = row.getCells(); int index = 0; for (String text : cellTexts) { assertThat(rowCells[index++].getPhrase().getContent(), is(text)); } } }