diff --git a/api/src/main/java/org/openmrs/validator/VisitValidator.java b/api/src/main/java/org/openmrs/validator/VisitValidator.java
index 19c54d34e12b..608fe4c6ab2d 100644
--- a/api/src/main/java/org/openmrs/validator/VisitValidator.java
+++ b/api/src/main/java/org/openmrs/validator/VisitValidator.java
@@ -111,8 +111,15 @@ public void validate(Object target, Errors errors) {
// Skipping validation if the patient is not set or not yet persisted
boolean nonExistingPatient = visit.getPatient() == null || visit.getPatient().getId() == null;
+ Visit existingVisit = Context.getVisitService().getVisitByUuid(visit.getUuid());
+
+ boolean endingVisit = existingVisit != null &&
+ existingVisit.getStopDatetime() == null &&
+ visit.getStopDatetime() != null
+ && existingVisit.getStartDatetime().equals(visit.getStartDatetime());
+
// check for overlapping visits
- if (!nonExistingPatient && disallowOverlappingVisits()) {
+ if (!nonExistingPatient && disallowOverlappingVisits() && !endingVisit) {
VisitSearchCriteria visitSearchCriteria = new VisitSearchCriteriaBuilder()
.patient(visit.getPatient())
.maxStartDatetime(visit.getStopDatetime())
diff --git a/api/src/test/java/org/openmrs/validator/VisitValidatorTest.java b/api/src/test/java/org/openmrs/validator/VisitValidatorTest.java
index abaefa265ab9..2c004bac4a87 100755
--- a/api/src/test/java/org/openmrs/validator/VisitValidatorTest.java
+++ b/api/src/test/java/org/openmrs/validator/VisitValidatorTest.java
@@ -407,6 +407,68 @@ public void validate_shouldRejectOverlappingActiveVisits() {
assertTrue(errors.hasFieldErrors("startDatetime"));
}
+ /**
+ * @see VisitValidator#validate(Object, org.springframework.validation.Errors)
+ * Should skip validation if it is an end visit call and start date is not changed
+ */
+ @Test
+ public void validate_shouldNotRejectOnVisitOverlapDuringEndVisit() {
+
+ // active visit: |---------------->
+ // overlapping visit: |--|
+ // ended active visit: |----------|
+
+ String activeVisitUuid = "c2639863-cbbe-44bb-986d-8a4820f8ae14";
+ Visit activeVisit = Context.getVisitService().getVisitByUuid(activeVisitUuid);
+
+ String newStopDateTime = "2014-02-06T00:00:00";
+
+ // make a clone and update the visit with an end date
+ Visit updatedVisit = new Visit();
+ updatedVisit.setVisitId(activeVisit.getVisitId());
+ updatedVisit.setUuid(activeVisit.getUuid());
+ updatedVisit.setPatient(activeVisit.getPatient());
+ updatedVisit.setStartDatetime(activeVisit.getStartDatetime());
+ updatedVisit.setVisitType(activeVisit.getVisitType());
+ updatedVisit.setStopDatetime(parseIsoDate(newStopDateTime));
+
+ Errors errors = new BindException(updatedVisit, "visit");
+ new VisitValidator().validate(updatedVisit, errors);
+
+ assertFalse(errors.hasFieldErrors("startDatetime"));
+ }
+
+ /**
+ * @see VisitValidator#validate(Object, org.springframework.validation.Errors)
+ * Should skip validation if it is an end visit call and start date is not changed
+ */
+ @Test
+ public void validate_shouldRejectOnVisitOverlapDuringEndVisitWithStartDateUpdated() {
+ // active visit: |---------------->
+ // overlapping visit: |--|
+ // ended active visit: |----------|
+
+ String activeVisitUuid = "c2639863-cbbe-44bb-986d-8a4820f8ae14";
+ Visit activeVisit = Context.getVisitService().getVisitByUuid(activeVisitUuid);
+
+ String newStartDateTime = "2014-02-04T00:00:00";
+ String newStopDateTime = "2014-02-06T00:00:00";
+
+ // make a clone and update the visit with an end date
+ Visit updatedVisit = new Visit();
+ updatedVisit.setVisitId(activeVisit.getVisitId());
+ updatedVisit.setUuid(activeVisit.getUuid());
+ updatedVisit.setPatient(activeVisit.getPatient());
+ updatedVisit.setVisitType(activeVisit.getVisitType());
+ updatedVisit.setStartDatetime(parseIsoDate(newStartDateTime));
+ updatedVisit.setStopDatetime(parseIsoDate(newStopDateTime));
+
+ Errors errors = new BindException(updatedVisit, "visit");
+ new VisitValidator().validate(updatedVisit, errors);
+
+ assertTrue(errors.hasFieldErrors("startDatetime"));
+ }
+
/**
* @see VisitValidator#validate(Object, org.springframework.validation.Errors)
* This test verifies that updating an existing visit does not result in a rejection
diff --git a/api/src/test/resources/org/openmrs/validator/include/VisitValidatorTest.xml b/api/src/test/resources/org/openmrs/validator/include/VisitValidatorTest.xml
index 5fe8767066d3..d1bb682c5975 100644
--- a/api/src/test/resources/org/openmrs/validator/include/VisitValidatorTest.xml
+++ b/api/src/test/resources/org/openmrs/validator/include/VisitValidatorTest.xml
@@ -28,5 +28,6 @@
-
+
+