← Back to team overview

dhis2-devs team mailing list archive

[Branch ~dhis2-devs-core/dhis2/trunk] Rev 5719: (patient) Add function to create valiation for date-fields in case entry.

 

------------------------------------------------------------
revno: 5719
committer: Tran Chau <tran.hispvietnam@xxxxxxxxx>
branch nick: dhis2
timestamp: Fri 2012-01-13 09:14:28 +0700
message:
  (patient) Add function to create valiation for date-fields in case entry.
added:
  dhis-2/dhis-web/dhis-web-maintenance/dhis-web-maintenance-patient/src/main/java/org/hisp/dhis/patient/action/validation/GetDateDataElementsAction.java
  dhis-2/dhis-web/dhis-web-maintenance/dhis-web-maintenance-patient/src/main/webapp/dhis-web-maintenance-patient/addDateProgramValidationForm.vm
  dhis-2/dhis-web/dhis-web-maintenance/dhis-web-maintenance-patient/src/main/webapp/dhis-web-maintenance-patient/dateProgramValidationForm.vm
modified:
  dhis-2/dhis-api/src/main/java/org/hisp/dhis/program/ProgramValidation.java
  dhis-2/dhis-api/src/main/java/org/hisp/dhis/program/ProgramValidationService.java
  dhis-2/dhis-api/src/main/java/org/hisp/dhis/program/ProgramValidationStore.java
  dhis-2/dhis-services/dhis-service-patient/src/main/java/org/hisp/dhis/patient/startup/TableAlteror.java
  dhis-2/dhis-services/dhis-service-patient/src/main/java/org/hisp/dhis/program/DefaultProgramValidationService.java
  dhis-2/dhis-services/dhis-service-patient/src/main/java/org/hisp/dhis/program/hibernate/HibernateProgramValidationStore.java
  dhis-2/dhis-services/dhis-service-patient/src/main/resources/META-INF/dhis/beans.xml
  dhis-2/dhis-services/dhis-service-patient/src/main/resources/org/hisp/dhis/program/hibernate/ProgramValidation.hbm.xml
  dhis-2/dhis-web/dhis-web-caseentry/src/main/java/org/hisp/dhis/caseentry/action/caseentry/SaveDateValueAction.java
  dhis-2/dhis-web/dhis-web-caseentry/src/main/java/org/hisp/dhis/caseentry/action/caseentry/ValidateProgramInstanceAction.java
  dhis-2/dhis-web/dhis-web-caseentry/src/main/resources/META-INF/dhis/beans.xml
  dhis-2/dhis-web/dhis-web-caseentry/src/main/resources/org/hisp/dhis/caseentry/i18n_module.properties
  dhis-2/dhis-web/dhis-web-caseentry/src/main/webapp/dhis-web-caseentry/javascript/entry.js
  dhis-2/dhis-web/dhis-web-caseentry/src/main/webapp/dhis-web-caseentry/validationResult.vm
  dhis-2/dhis-web/dhis-web-maintenance/dhis-web-maintenance-patient/src/main/java/org/hisp/dhis/patient/action/validation/AddProgramValidationAction.java
  dhis-2/dhis-web/dhis-web-maintenance/dhis-web-maintenance-patient/src/main/java/org/hisp/dhis/patient/action/validation/GetProgramValidationListAction.java
  dhis-2/dhis-web/dhis-web-maintenance/dhis-web-maintenance-patient/src/main/resources/META-INF/dhis/beans.xml
  dhis-2/dhis-web/dhis-web-maintenance/dhis-web-maintenance-patient/src/main/resources/org/hisp/dhis/patient/i18n_module.properties
  dhis-2/dhis-web/dhis-web-maintenance/dhis-web-maintenance-patient/src/main/resources/struts.xml
  dhis-2/dhis-web/dhis-web-maintenance/dhis-web-maintenance-patient/src/main/webapp/dhis-web-maintenance-patient/addMultiProgramValidationForm.vm
  dhis-2/dhis-web/dhis-web-maintenance/dhis-web-maintenance-patient/src/main/webapp/dhis-web-maintenance-patient/addSingleProgramValidationForm.vm
  dhis-2/dhis-web/dhis-web-maintenance/dhis-web-maintenance-patient/src/main/webapp/dhis-web-maintenance-patient/javascript/programValidation.js
  dhis-2/dhis-web/dhis-web-maintenance/dhis-web-maintenance-patient/src/main/webapp/dhis-web-maintenance-patient/programValidationList.vm


--
lp:dhis2
https://code.launchpad.net/~dhis2-devs-core/dhis2/trunk

Your team DHIS 2 developers is subscribed to branch lp:dhis2.
To unsubscribe from this branch go to https://code.launchpad.net/~dhis2-devs-core/dhis2/trunk/+edit-subscription
=== modified file 'dhis-2/dhis-api/src/main/java/org/hisp/dhis/program/ProgramValidation.java'
--- dhis-2/dhis-api/src/main/java/org/hisp/dhis/program/ProgramValidation.java	2012-01-06 04:56:54 +0000
+++ dhis-2/dhis-api/src/main/java/org/hisp/dhis/program/ProgramValidation.java	2012-01-13 02:14:28 +0000
@@ -29,13 +29,12 @@
 
 import java.io.Serializable;
 
-
 /**
  * @author Chau Thu Tran
  * @version $ ProgramValidation.java Apr 28, 2011 10:27:29 AM $
  */
 public class ProgramValidation
-implements Serializable
+    implements Serializable
 {
     /**
      * Determines if a de-serialized file is compatible with this class.
@@ -47,6 +46,24 @@
     public static final String SEPARATOR_OBJECT = ":";
 
     public static String OBJECT_PROGRAM_STAGE_DATAELEMENT = "DE";
+    
+
+    public int BEFORE_CURRENT_DATE = 1;
+
+    public int BEFORE_OR_EQUALS_TO_CURRENT_DATE = 2;
+
+    public int AFTER_CURRENT_DATE = 3;
+
+    public int AFTER_OR_EQUALS_TO_CURRENT_DATE = 4;
+    
+
+    public int BEFORE_DUE_DATE = -1;
+
+    public int BEFORE_OR_EQUALS_TO_DUE_DATE = -2;
+
+    public int AFTER_DUE_DATE = -3;
+
+    public int AFTER_OR_EQUALS_TO_DUE_DATE = -4;
 
     // -------------------------------------------------------------------------
     // Fields
@@ -62,6 +79,8 @@
 
     private Program program;
 
+    private Boolean dateType;
+
     // -------------------------------------------------------------------------
     // Constructor
     // -------------------------------------------------------------------------
@@ -79,23 +98,27 @@
         this.program = program;
     }
 
+    public ProgramValidation( String description, String leftSide, String rightSide, Program program, Boolean dateType )
+    {
+        this.description = description;
+        this.leftSide = leftSide;
+        this.rightSide = rightSide;
+        this.program = program;
+        this.dateType = dateType;
+    }
+
     // -------------------------------------------------------------------------
     // hashCode() and equals()
     // -------------------------------------------------------------------------
 
-    public int getId()
-    {
-        return id;
-    }
-
     @Override
     public int hashCode()
     {
         final int prime = 31;
         int result = 1;
-        result = prime * result + ( ( leftSide == null ) ? 0 : leftSide.hashCode() );
-        result = prime * result + ( ( program == null ) ? 0 : program.hashCode() );
-        result = prime * result + ( ( rightSide == null)  ? 0 : rightSide.hashCode() );
+        result = prime * result + ((leftSide == null) ? 0 : leftSide.hashCode());
+        result = prime * result + ((program == null) ? 0 : program.hashCode());
+        result = prime * result + ((rightSide == null) ? 0 : rightSide.hashCode());
         return result;
     }
 
@@ -106,19 +129,19 @@
         {
             return true;
         }
-        
+
         if ( obj == null )
         {
             return false;
         }
-        
+
         if ( getClass() != obj.getClass() )
         {
             return false;
         }
-        
+
         ProgramValidation other = (ProgramValidation) obj;
-        
+
         if ( leftSide == null )
         {
             if ( other.leftSide != null )
@@ -130,7 +153,7 @@
         {
             return false;
         }
-        
+
         if ( program == null )
         {
             if ( other.program != null )
@@ -142,7 +165,7 @@
         {
             return false;
         }
-        
+
         if ( rightSide == null )
         {
             if ( other.rightSide != null )
@@ -154,7 +177,7 @@
         {
             return false;
         }
-        
+
         return true;
     }
 
@@ -162,6 +185,11 @@
     // Getters && Setters
     // -------------------------------------------------------------------------
 
+    public int getId()
+    {
+        return id;
+    }
+
     public void setId( int id )
     {
         this.id = id;
@@ -207,4 +235,13 @@
         this.program = program;
     }
 
+    public Boolean getDateType()
+    {
+        return dateType;
+    }
+
+    public void setDateType( Boolean dateType )
+    {
+        this.dateType = dateType;
+    }
 }

=== modified file 'dhis-2/dhis-api/src/main/java/org/hisp/dhis/program/ProgramValidationService.java'
--- dhis-2/dhis-api/src/main/java/org/hisp/dhis/program/ProgramValidationService.java	2012-01-06 04:56:54 +0000
+++ dhis-2/dhis-api/src/main/java/org/hisp/dhis/program/ProgramValidationService.java	2012-01-13 02:14:28 +0000
@@ -29,6 +29,7 @@
 
 import java.util.Collection;
 
+import org.hisp.dhis.i18n.I18nFormat;
 import org.hisp.dhis.organisationunit.OrganisationUnit;
 
 /**
@@ -51,5 +52,12 @@
 
     Collection<ProgramValidation> getProgramValidation( Program program );
 
-    boolean runValidation( ProgramValidation validation, ProgramInstance programInstance, OrganisationUnit orgunit );
+    Collection<ProgramValidation> getProgramValidation( Program program, Boolean dateType );
+    
+    Collection<ProgramValidation> getProgramValidation( ProgramStage programStage );
+
+    Collection<ProgramValidation> getProgramValidation( ProgramStageDataElement psdataElement );
+
+    boolean runValidation( ProgramValidation validation, ProgramStageInstance programStageInstance, OrganisationUnit orgunit,
+        I18nFormat format );
 }

=== modified file 'dhis-2/dhis-api/src/main/java/org/hisp/dhis/program/ProgramValidationStore.java'
--- dhis-2/dhis-api/src/main/java/org/hisp/dhis/program/ProgramValidationStore.java	2012-01-06 04:56:54 +0000
+++ dhis-2/dhis-api/src/main/java/org/hisp/dhis/program/ProgramValidationStore.java	2012-01-13 02:14:28 +0000
@@ -40,4 +40,6 @@
     String ID = ProgramValidation.class.getName();
 
     Collection<ProgramValidation> get( Program program );
+    
+    Collection<ProgramValidation> get( Program program, Boolean dateType );
 }

=== modified file 'dhis-2/dhis-services/dhis-service-patient/src/main/java/org/hisp/dhis/patient/startup/TableAlteror.java'
--- dhis-2/dhis-services/dhis-service-patient/src/main/java/org/hisp/dhis/patient/startup/TableAlteror.java	2012-01-11 05:31:53 +0000
+++ dhis-2/dhis-services/dhis-service-patient/src/main/java/org/hisp/dhis/patient/startup/TableAlteror.java	2012-01-13 02:14:28 +0000
@@ -118,6 +118,7 @@
 
         updateStageInProgram();
 
+        executeSql( "UPDATE programvalidation SET dateType = false WHERE dateType is null");
     }
 
     // -------------------------------------------------------------------------

=== modified file 'dhis-2/dhis-services/dhis-service-patient/src/main/java/org/hisp/dhis/program/DefaultProgramValidationService.java'
--- dhis-2/dhis-services/dhis-service-patient/src/main/java/org/hisp/dhis/program/DefaultProgramValidationService.java	2012-01-11 05:31:53 +0000
+++ dhis-2/dhis-services/dhis-service-patient/src/main/java/org/hisp/dhis/program/DefaultProgramValidationService.java	2012-01-13 02:14:28 +0000
@@ -32,6 +32,9 @@
 import static org.hisp.dhis.program.ProgramValidation.SEPARATOR_OBJECT;
 
 import java.util.Collection;
+import java.util.Date;
+import java.util.HashSet;
+import java.util.Iterator;
 import java.util.regex.Matcher;
 import java.util.regex.Pattern;
 
@@ -39,6 +42,7 @@
 import org.hisp.dhis.dataelement.DataElementCategoryOptionCombo;
 import org.hisp.dhis.dataelement.DataElementCategoryService;
 import org.hisp.dhis.dataelement.DataElementService;
+import org.hisp.dhis.i18n.I18nFormat;
 import org.hisp.dhis.organisationunit.OrganisationUnit;
 import org.hisp.dhis.patientdatavalue.PatientDataValue;
 import org.hisp.dhis.patientdatavalue.PatientDataValueService;
@@ -53,14 +57,15 @@
 public class DefaultProgramValidationService
     implements ProgramValidationService
 {
+    private final String regExp = "\\[" + OBJECT_PROGRAM_STAGE_DATAELEMENT + SEPARATOR_OBJECT + "([a-zA-Z0-9\\- ]+["
+        + SEPARATOR_ID + "[0-9]*]*)" + "\\]";
+
     private ProgramValidationStore validationStore;
 
     private ProgramStageService programStageService;
 
     private DataElementService dataElementService;
 
-    private ProgramStageInstanceService stageInstanceService;
-
     private PatientDataValueService valueService;
 
     private DataElementCategoryService categoryService;
@@ -89,11 +94,6 @@
         this.dataElementService = dataElementService;
     }
 
-    public void setStageInstanceService( ProgramStageInstanceService stageInstanceService )
-    {
-        this.stageInstanceService = stageInstanceService;
-    }
-
     public void setValueService( PatientDataValueService valueService )
     {
         this.valueService = valueService;
@@ -133,23 +133,27 @@
     }
 
     @Override
-    public boolean runValidation( ProgramValidation validation, ProgramInstance programInstance,
-        OrganisationUnit orgunit )
+    public boolean runValidation( ProgramValidation validation, ProgramStageInstance programStageInstance,
+        OrganisationUnit orgunit, I18nFormat format )
     {
-        // ---------------------------------------------------------------------
-        // parse left-expressions
-        // ---------------------------------------------------------------------
-
-        boolean resultLeft = runExpression( validation.getLeftSide(), programInstance, orgunit );
-
-        // ---------------------------------------------------------------------
-        // parse right-expressions
-        // ---------------------------------------------------------------------
-
-        boolean resultRight = runExpression( validation.getRightSide(), programInstance, orgunit );
-
-        return (resultLeft == resultRight);
-
+        if ( !validation.getDateType() )
+        {
+            // ---------------------------------------------------------------------
+            // parse left-expressions
+            // ---------------------------------------------------------------------
+
+            boolean resultLeft = runExpression( validation.getLeftSide(), programStageInstance, orgunit );
+
+            // ---------------------------------------------------------------------
+            // parse right-expressions
+            // ---------------------------------------------------------------------
+
+            boolean resultRight = runExpression( validation.getRightSide(), programStageInstance, orgunit );
+
+            return (resultLeft == resultRight);
+        }
+
+        return runDateExpression( validation, programStageInstance, orgunit, format );
     }
 
     public Collection<ProgramValidation> getProgramValidation( Program program )
@@ -157,11 +161,40 @@
         return validationStore.get( program );
     }
 
-    private boolean runExpression( String expression, ProgramInstance programInstance, OrganisationUnit orgunit )
-    {
-        final String regExp = "\\[" + OBJECT_PROGRAM_STAGE_DATAELEMENT + SEPARATOR_OBJECT + "([a-zA-Z0-9\\- ]+["
-            + SEPARATOR_ID + "[0-9]*]*)" + "\\]";
-
+    public Collection<ProgramValidation> getProgramValidation( Program program, Boolean dateType )
+    {
+        return validationStore.get( program, dateType );
+    }
+
+    public Collection<ProgramValidation> getProgramValidation( ProgramStageDataElement psdataElement )
+    {
+        Collection<ProgramValidation> programValidation = validationStore.get( psdataElement.getProgramStage()
+            .getProgram() );
+
+        Collection<ProgramValidation> result = new HashSet<ProgramValidation>();
+
+        for ( ProgramValidation validation : programValidation )
+        {
+            Collection<DataElement> dataElements = getDataElementInExpression( validation );
+            Collection<ProgramStage> programStages = getProgramStageInExpression( validation );
+
+            if ( dataElements.contains( psdataElement.getDataElement() )
+                && programStages.contains( psdataElement.getProgramStage() ) )
+            {
+                result.add( validation );
+            }
+        }
+
+        return result;
+    }
+
+    // -------------------------------------------------------------------------
+    // Supportive methods
+    // -------------------------------------------------------------------------
+
+    private boolean runExpression( String expression, ProgramStageInstance programStageInstance,
+        OrganisationUnit orgunit )
+    {
         StringBuffer description = new StringBuffer();
 
         Pattern pattern = Pattern.compile( regExp );
@@ -171,26 +204,8 @@
         while ( matcher.find() )
         {
             String match = matcher.group();
-            match = match.replaceAll( "[\\[\\]]", "" );
-
-            String[] info = match.split( SEPARATOR_OBJECT );
-            String[] ids = info[1].split( SEPARATOR_ID );
-
-            int programStageId = Integer.parseInt( ids[0] );
-            ProgramStage programStage = programStageService.getProgramStage( programStageId );
-
-            int dataElementId = Integer.parseInt( ids[1] );
-            DataElement dataElement = dataElementService.getDataElement( dataElementId );
-
-            int optionComboId = Integer.parseInt( ids[2] );
-            DataElementCategoryOptionCombo optionCombo = categoryService
-                .getDataElementCategoryOptionCombo( optionComboId );
-
-            ProgramStageInstance stageInstance = stageInstanceService.getProgramStageInstance( programInstance,
-                programStage );
-
-            PatientDataValue dataValue = valueService.getPatientDataValue( stageInstance, dataElement, optionCombo,
-                orgunit );
+
+            PatientDataValue dataValue = getPatientDataValue( match, programStageInstance, orgunit );
 
             if ( dataValue == null )
             {
@@ -208,4 +223,169 @@
 
         return (parser.getValue() == 1.0);
     }
+
+    public boolean runDateExpression( ProgramValidation programValidation, ProgramStageInstance programStageInstance,
+        OrganisationUnit orgunit, I18nFormat format )
+    {
+        Pattern pattern = Pattern.compile( regExp );
+
+        Matcher matcher = pattern.matcher( programValidation.getLeftSide() );
+
+        if ( matcher.find() )
+        {
+            String match = matcher.group();
+
+            PatientDataValue dataValue = getPatientDataValue( match, programStageInstance, orgunit );
+
+            if ( dataValue == null )
+            {
+                return true;
+            }
+
+            int rightSide = Integer.parseInt( programValidation.getRightSide() );
+            Date dueDate = dataValue.getProgramStageInstance().getDueDate();
+            Date currentDate = dataValue.getTimestamp();
+            Date value = format.parseDate( dataValue.getValue() );
+
+            switch ( rightSide )
+            {
+            case 1:
+                return value.before( currentDate );
+            case 2:
+                return (value.before( currentDate ) || value.equals( currentDate ));
+            case 3:
+                return value.after( currentDate );
+            case 4:
+                return (value.after( currentDate ) || value.equals( currentDate ));
+            case -1:
+                return value.before( dueDate );
+            case -2:
+                return (value.before( dueDate ) || value.equals( dueDate ));
+            case -3:
+                return value.after( dueDate );
+            case -4:
+                return (value.after( dueDate ) || value.equals( dueDate ));
+            default:
+                return true;
+            }
+        }
+
+        return true;
+    }
+
+    public Collection<ProgramValidation> getProgramValidation( ProgramStage programStage )
+    {
+        Collection<ProgramValidation> programValidation = getProgramValidation( programStage.getProgram() );
+
+        Iterator<ProgramValidation> iter = programValidation.iterator();
+
+        Pattern pattern = Pattern.compile( regExp );
+
+        while ( iter.hasNext() )
+        {
+            ProgramValidation validation = iter.next();
+
+            String expression = validation.getLeftSide() + " " + validation.getRightSide();
+            Matcher matcher = pattern.matcher( expression );
+
+            boolean flag = false;
+            while ( matcher.find() )
+            {
+                String match = matcher.group();
+                match = match.replaceAll( "[\\[\\]]", "" );
+
+                String[] info = match.split( SEPARATOR_OBJECT );
+                String[] ids = info[1].split( SEPARATOR_ID );
+
+                int programStageId = Integer.parseInt( ids[0] );
+
+                if ( programStageId == programStage.getId() )
+                {
+                    flag = true;
+                    break;
+                }
+            }
+
+            if ( !flag )
+            {
+                iter.remove();
+            }
+        }
+
+        return programValidation;
+    }
+
+    // -------------------------------------------------------------------------
+    // Supportive methods
+    // -------------------------------------------------------------------------
+
+    private PatientDataValue getPatientDataValue( String match, ProgramStageInstance programStageInstance,
+        OrganisationUnit orgunit )
+    {
+        match = match.replaceAll( "[\\[\\]]", "" );
+
+        String[] info = match.split( SEPARATOR_OBJECT );
+        String[] ids = info[1].split( SEPARATOR_ID );
+
+        int dataElementId = Integer.parseInt( ids[1] );
+        DataElement dataElement = dataElementService.getDataElement( dataElementId );
+
+        int optionComboId = Integer.parseInt( ids[2] );
+        DataElementCategoryOptionCombo optionCombo = categoryService.getDataElementCategoryOptionCombo( optionComboId );
+
+        PatientDataValue dataValue = valueService.getPatientDataValue( programStageInstance, dataElement, optionCombo,
+            orgunit );
+
+        return dataValue;
+    }
+
+    private Collection<DataElement> getDataElementInExpression( ProgramValidation programValidation )
+    {
+        Collection<DataElement> dataElements = new HashSet<DataElement>();
+
+        Pattern pattern = Pattern.compile( regExp );
+        String expression = programValidation.getLeftSide() + " " + programValidation.getRightSide();
+        Matcher matcher = pattern.matcher( expression );
+
+        while ( matcher.find() )
+        {
+            String match = matcher.group();
+            match = match.replaceAll( "[\\[\\]]", "" );
+
+            String[] info = match.split( SEPARATOR_OBJECT );
+            String[] ids = info[1].split( SEPARATOR_ID );
+
+            int dataElementId = Integer.parseInt( ids[1] );
+            DataElement dataElement = dataElementService.getDataElement( dataElementId );
+
+            dataElements.add( dataElement );
+        }
+
+        return dataElements;
+    }
+
+    private Collection<ProgramStage> getProgramStageInExpression( ProgramValidation programValidation )
+    {
+        Collection<ProgramStage> programStages = new HashSet<ProgramStage>();
+
+        Pattern pattern = Pattern.compile( regExp );
+        String expression = programValidation.getLeftSide() + " " + programValidation.getRightSide();
+        Matcher matcher = pattern.matcher( expression );
+
+        while ( matcher.find() )
+        {
+            String match = matcher.group();
+            match = match.replaceAll( "[\\[\\]]", "" );
+
+            String[] info = match.split( SEPARATOR_OBJECT );
+            String[] ids = info[1].split( SEPARATOR_ID );
+
+            int programStageId = Integer.parseInt( ids[0] );
+            ProgramStage programStage = programStageService.getProgramStage( programStageId );
+
+            programStages.add( programStage );
+        }
+
+        return programStages;
+    }
 }

=== modified file 'dhis-2/dhis-services/dhis-service-patient/src/main/java/org/hisp/dhis/program/hibernate/HibernateProgramValidationStore.java'
--- dhis-2/dhis-services/dhis-service-patient/src/main/java/org/hisp/dhis/program/hibernate/HibernateProgramValidationStore.java	2012-01-11 05:31:53 +0000
+++ dhis-2/dhis-services/dhis-service-patient/src/main/java/org/hisp/dhis/program/hibernate/HibernateProgramValidationStore.java	2012-01-13 02:14:28 +0000
@@ -49,4 +49,9 @@
         return getCriteria( Restrictions.eq( "program", program ) ).list();
     }
 
+    @SuppressWarnings( "unchecked" )
+    public Collection<ProgramValidation> get( Program program, Boolean dateType )
+    {
+        return getCriteria( Restrictions.eq( "program", program ), Restrictions.eq( "dateType", dateType ) ).list();
+    }
 }

=== modified file 'dhis-2/dhis-services/dhis-service-patient/src/main/resources/META-INF/dhis/beans.xml'
--- dhis-2/dhis-services/dhis-service-patient/src/main/resources/META-INF/dhis/beans.xml	2012-01-11 05:31:53 +0000
+++ dhis-2/dhis-services/dhis-service-patient/src/main/resources/META-INF/dhis/beans.xml	2012-01-13 02:14:28 +0000
@@ -232,8 +232,6 @@
 			ref="org.hisp.dhis.dataelement.DataElementService" />
 		<property name="categoryService"
 			ref="org.hisp.dhis.dataelement.DataElementCategoryService" />
-		<property name="stageInstanceService"
-			ref="org.hisp.dhis.program.ProgramStageInstanceService" />
 		<property name="valueService"
 			ref="org.hisp.dhis.patientdatavalue.PatientDataValueService" />
 	</bean>

=== modified file 'dhis-2/dhis-services/dhis-service-patient/src/main/resources/org/hisp/dhis/program/hibernate/ProgramValidation.hbm.xml'
--- dhis-2/dhis-services/dhis-service-patient/src/main/resources/org/hisp/dhis/program/hibernate/ProgramValidation.hbm.xml	2011-05-28 21:25:46 +0000
+++ dhis-2/dhis-services/dhis-service-patient/src/main/resources/org/hisp/dhis/program/hibernate/ProgramValidation.hbm.xml	2012-01-13 02:14:28 +0000
@@ -19,6 +19,8 @@
 
 		<many-to-one name="program" class="org.hisp.dhis.program.Program"
 			column="programid" not-null="true" foreign-key="fk_programvalidation_programid" />
+			
+		<property name="dateType" />
 
 	</class>
 </hibernate-mapping>

=== modified file 'dhis-2/dhis-web/dhis-web-caseentry/src/main/java/org/hisp/dhis/caseentry/action/caseentry/SaveDateValueAction.java'
--- dhis-2/dhis-web/dhis-web-caseentry/src/main/java/org/hisp/dhis/caseentry/action/caseentry/SaveDateValueAction.java	2011-07-08 07:22:42 +0000
+++ dhis-2/dhis-web/dhis-web-caseentry/src/main/java/org/hisp/dhis/caseentry/action/caseentry/SaveDateValueAction.java	2012-01-13 02:14:28 +0000
@@ -34,12 +34,9 @@
 import org.hisp.dhis.dataelement.DataElement;
 import org.hisp.dhis.dataelement.DataElementCategoryOptionCombo;
 import org.hisp.dhis.dataelement.DataElementService;
-import org.hisp.dhis.i18n.I18n;
-import org.hisp.dhis.i18n.I18nFormat;
 import org.hisp.dhis.organisationunit.OrganisationUnit;
 import org.hisp.dhis.patientdatavalue.PatientDataValue;
 import org.hisp.dhis.patientdatavalue.PatientDataValueService;
-import org.hisp.dhis.program.Program;
 import org.hisp.dhis.program.ProgramStageInstance;
 import org.hisp.dhis.program.ProgramStageInstanceService;
 
@@ -86,13 +83,6 @@
         this.selectedStateManager = selectedStateManager;
     }
 
-    private I18nFormat format;
-
-    public void setFormat( I18nFormat format )
-    {
-        this.format = format;
-    }
-
     // -------------------------------------------------------------------------
     // Input/Output
     // -------------------------------------------------------------------------
@@ -142,13 +132,6 @@
         return message;
     }
 
-    private I18n i18n;
-
-    public void setI18n( I18n i18n )
-    {
-        this.i18n = i18n;
-    }
-
     // -------------------------------------------------------------------------
     // Implementation Action
     // -------------------------------------------------------------------------
@@ -164,8 +147,6 @@
 
         ProgramStageInstance programStageInstance = selectedStateManager.getSelectedProgramStageInstance();
 
-        Program program = programStageInstance.getProgramInstance().getProgram();
-
         DataElement dataElement = dataElementService.getDataElement( dataElementId );
 
         DataElementCategoryOptionCombo optionCombo = dataElement.getCategoryCombo().getOptionCombos().iterator().next();
@@ -179,33 +160,6 @@
         }
 
         // ---------------------------------------------------------------------
-        // Check inputed value:
-        // value <= DueDate + program.maxDaysAllowedInputData
-        // ---------------------------------------------------------------------
-
-        if ( value != null )
-        {
-            Date dateValue = format.parseDate( value );
-
-            Date dueDate = programStageInstance.getDueDate();
-
-            long diffMillis = dateValue.getTime() - dueDate.getTime();
-
-            long diffMaxDays = diffMillis / 86400000;
-
-            if ( diffMaxDays > program.getMaxDaysAllowedInputData() )
-            {
-                statusCode = 2;
-
-                message = i18n.getString( "date_is_less_then_or_equals_plus_no_max_days" ) + " " + " ( "
-                    + i18n.getString( "max_days" ) + " : " + program.getMaxDaysAllowedInputData()
-                    + i18n.getString( "days" ) + " )";
-
-                return SUCCESS;
-            }
-        }
-
-        // ---------------------------------------------------------------------
         // Save value
         // ---------------------------------------------------------------------
 

=== modified file 'dhis-2/dhis-web/dhis-web-caseentry/src/main/java/org/hisp/dhis/caseentry/action/caseentry/ValidateProgramInstanceAction.java'
--- dhis-2/dhis-web/dhis-web-caseentry/src/main/java/org/hisp/dhis/caseentry/action/caseentry/ValidateProgramInstanceAction.java	2011-12-26 10:07:59 +0000
+++ dhis-2/dhis-web/dhis-web-caseentry/src/main/java/org/hisp/dhis/caseentry/action/caseentry/ValidateProgramInstanceAction.java	2012-01-13 02:14:28 +0000
@@ -34,9 +34,11 @@
 import java.util.Map;
 import java.util.Set;
 
+import org.hisp.dhis.caseaggregation.CaseAggregationConditionService;
 import org.hisp.dhis.caseentry.state.SelectedStateManager;
 import org.hisp.dhis.dataelement.DataElement;
 import org.hisp.dhis.i18n.I18n;
+import org.hisp.dhis.i18n.I18nFormat;
 import org.hisp.dhis.organisationunit.OrganisationUnit;
 import org.hisp.dhis.patientdatavalue.PatientDataValue;
 import org.hisp.dhis.patientdatavalue.PatientDataValueService;
@@ -68,13 +70,17 @@
     private PatientDataValueService patientDataValueService;
 
     private ProgramValidationService programValidationService;
-    
+
+    private CaseAggregationConditionService aggregationConditionService;
+
     // -------------------------------------------------------------------------
     // Input
     // -------------------------------------------------------------------------
-    
+
     private I18n i18n;
 
+    private I18nFormat format;
+
     // -------------------------------------------------------------------------
     // Output
     // -------------------------------------------------------------------------
@@ -83,6 +89,10 @@
 
     private List<ProgramValidation> programValidations;
 
+    private Map<Integer, String> leftsideFormulaMap;
+
+    private Map<Integer, String> rightsideFormulaMap;
+
     // -------------------------------------------------------------------------
     // Getters && Setters
     // -------------------------------------------------------------------------
@@ -91,7 +101,27 @@
     {
         this.selectedStateManager = selectedStateManager;
     }
-    
+
+    public void setFormat( I18nFormat format )
+    {
+        this.format = format;
+    }
+
+    public void setAggregationConditionService( CaseAggregationConditionService aggregationConditionService )
+    {
+        this.aggregationConditionService = aggregationConditionService;
+    }
+
+    public Map<Integer, String> getLeftsideFormulaMap()
+    {
+        return leftsideFormulaMap;
+    }
+
+    public Map<Integer, String> getRightsideFormulaMap()
+    {
+        return rightsideFormulaMap;
+    }
+
     public List<ProgramValidation> getProgramValidations()
     {
         return programValidations;
@@ -127,7 +157,6 @@
         return selectedStateManager;
     }
 
-
     // -------------------------------------------------------------------------
     // Action implementation
     // -------------------------------------------------------------------------
@@ -144,12 +173,12 @@
         // Get selected objects
         // ---------------------------------------------------------------------
 
-        OrganisationUnit organisationUnit = selectedStateManager.getSelectedOrganisationUnit( );
+        OrganisationUnit organisationUnit = selectedStateManager.getSelectedOrganisationUnit();
 
         ProgramStageInstance programStageInstance = selectedStateManager.getSelectedProgramStageInstance();
 
         ProgramStage programStage = programStageInstance.getProgramStage();
-        
+
         // ---------------------------------------------------------------------
         // Get selected objects
         // ---------------------------------------------------------------------
@@ -167,8 +196,8 @@
         // Check validations for dataelement into multi-stages
         // ---------------------------------------------------------------------
 
-        runProgramValidation( programValidationService.getProgramValidation( programStageInstance.getProgramInstance().getProgram() ),
-            programStageInstance.getProgramInstance(), organisationUnit );
+        runProgramValidation( programValidationService.getProgramValidation( programStageInstance.getProgramStage() ),
+            programStageInstance, organisationUnit );
 
         return SUCCESS;
     }
@@ -179,8 +208,8 @@
 
     /**
      * ------------------------------------------------------------------------
-     * // Check value of the dataElment into previous . // If the value exists,
-     * allow users to enter data of // the dataElement into the
+     * // Check value of the dataElment into previous. // If the value
+     * exists,allow users to enter data of // the dataElement into the
      * programStageInstance // Else, disable Input-field of the dataElement
      * ------------------------------------------------------------------------
      **/
@@ -191,9 +220,9 @@
         ProgramInstance programInstance = programStageInstance.getProgramInstance();
         List<ProgramStage> stages = new ArrayList<ProgramStage>( programInstance.getProgram().getProgramStages() );
 
-        int index = stages.indexOf( programStageInstance.getProgramStage() );
+        int index = programStageInstance.getStageInProgram();
 
-        if ( index != -1 && index != 0 )
+        if ( index > 0 )
         {
             ProgramStage prevStage = stages.get( index - 1 );
             ProgramStageInstance prevStageInstance = programStageInstanceService.getProgramStageInstance(
@@ -213,13 +242,15 @@
 
     }
 
-    private void runProgramValidation( Collection<ProgramValidation> validations, ProgramInstance programInstance, OrganisationUnit orgunit )
+    private void runProgramValidation( Collection<ProgramValidation> validations,
+        ProgramStageInstance programStageInstance, OrganisationUnit orgunit )
     {
         if ( validations != null )
         {
             for ( ProgramValidation validation : validations )
             {
-                boolean valid = programValidationService.runValidation( validation, programInstance, orgunit );
+                boolean valid = programValidationService.runValidation( validation, programStageInstance, orgunit,
+                    format );
 
                 if ( !valid )
                 {
@@ -227,5 +258,64 @@
                 }
             }
         }
+        
+        if ( !programValidations.isEmpty() )
+        {
+            leftsideFormulaMap = new HashMap<Integer, String>( programValidations.size() );
+            rightsideFormulaMap = new HashMap<Integer, String>( programValidations.size() );
+
+            for ( ProgramValidation validation : programValidations )
+            {
+                leftsideFormulaMap.put( validation.getId(), aggregationConditionService
+                    .getConditionDescription( validation.getLeftSide() ) );
+
+                if ( validation.getDateType() )
+                {
+                    int rightSide = Integer.parseInt( validation.getRightSide() );
+
+                    switch ( rightSide )
+                    {
+                    case 1:
+                        rightsideFormulaMap.put( validation.getId(), i18n.getString( "before_current_date" ) );
+                        break;
+                    case 2:
+                        rightsideFormulaMap.put( validation.getId(), i18n
+                            .getString( "before_or_equals_to_current_date" ) );
+                        break;
+                    case 3:
+                        rightsideFormulaMap.put( validation.getId(), i18n.getString( "after_current_date" ) );
+                        break;
+                    case 4:
+                        rightsideFormulaMap
+                            .put( validation.getId(), i18n.getString( "after_or_equals_to_current_date" ) );
+                        break;
+                    case -1:
+                        rightsideFormulaMap.put( validation.getId(), i18n.getString( "before_due_date" ) );
+                        break;
+                    case -2:
+                        rightsideFormulaMap.put( validation.getId(), i18n.getString( "before_or_equals_to_due_date" ) );
+                        break;
+                    case -3:
+                        rightsideFormulaMap.put( validation.getId(), i18n.getString( "after_due_date" ) );
+                        break;
+                    case -4:
+                        rightsideFormulaMap.put( validation.getId(), i18n.getString( "after_or_equals_to_due_date" ) );
+                        break;
+                    default:
+                        rightsideFormulaMap.put( validation.getId(), i18n.getString( "before_current_date" ) );
+                        break;
+                    }
+                }
+                else if ( validation.getRightSide().equals( "1==1" ) )
+                {
+                    rightsideFormulaMap.put( validation.getId(), "" );
+                }
+                else
+                {
+                    rightsideFormulaMap.put( validation.getId(), aggregationConditionService
+                        .getConditionDescription( validation.getRightSide() ) );
+                }
+            }
+        }
     }
 }

=== modified file 'dhis-2/dhis-web/dhis-web-caseentry/src/main/resources/META-INF/dhis/beans.xml'
--- dhis-2/dhis-web/dhis-web-caseentry/src/main/resources/META-INF/dhis/beans.xml	2012-01-11 05:31:53 +0000
+++ dhis-2/dhis-web/dhis-web-caseentry/src/main/resources/META-INF/dhis/beans.xml	2012-01-13 02:14:28 +0000
@@ -372,6 +372,8 @@
 			ref="org.hisp.dhis.patientdatavalue.PatientDataValueService" />
 		<property name="programValidationService"
 			ref="org.hisp.dhis.program.ProgramValidationService" />
+		<property name="aggregationConditionService"
+			ref="org.hisp.dhis.caseaggregation.CaseAggregationConditionService" />
 	</bean>
 	
 	<bean id="org.hisp.dhis.caseentry.action.caseentry.LoadAnonymousProgramsAction"

=== modified file 'dhis-2/dhis-web/dhis-web-caseentry/src/main/resources/org/hisp/dhis/caseentry/i18n_module.properties'
--- dhis-2/dhis-web/dhis-web-caseentry/src/main/resources/org/hisp/dhis/caseentry/i18n_module.properties	2012-01-11 07:19:34 +0000
+++ dhis-2/dhis-web/dhis-web-caseentry/src/main/resources/org/hisp/dhis/caseentry/i18n_module.properties	2012-01-13 02:14:28 +0000
@@ -456,4 +456,14 @@
 history_events = History events 
 integerValueOfAge = Age(years)
 reason = Reason
-patient_could_not_be_enrolled_due_to_following_enrollment_criteria=The beneficiary could not be enrolled due to the following enrollment criteria
\ No newline at end of file
+patient_could_not_be_enrolled_due_to_following_enrollment_criteria=The beneficiary could not be enrolled due to the following enrollment criteria
+before_current_date = Before current date
+before_or_equals_to_current_date = Before or equals to current date
+after_current_date = After current date
+after_or_equals_to_current_date = After or equals to current date
+before_due_date = Before due date
+before_or_equals_to_due_date = Before or equals to due date
+after_due_date = After due date
+after_or_equals_to_due_date = After or equals to due date
+leftSide = Left Side
+rightSide = Right Side
\ No newline at end of file

=== modified file 'dhis-2/dhis-web/dhis-web-caseentry/src/main/webapp/dhis-web-caseentry/javascript/entry.js'
--- dhis-2/dhis-web/dhis-web-caseentry/src/main/webapp/dhis-web-caseentry/javascript/entry.js	2012-01-11 08:34:43 +0000
+++ dhis-2/dhis-web/dhis-web-caseentry/src/main/webapp/dhis-web-caseentry/javascript/entry.js	2012-01-13 02:14:28 +0000
@@ -205,36 +205,6 @@
     });
 	
     var providedByAnotherFacility = document.getElementById( programStageId + '_' + dataElementId + '_facility' ).checked;
- 
-	if( fieldValue !="")
-    { 
-		var d2 = new Date( fieldValue );
-        if( d2 == 'Invalid Date' )
-        {
-            field.css({
-                "background-color":"#ffcc00"
-            });
-            window.alert('Incorrect format for date value. The correct format should be ' + dateFormat.replace('yy', 'yyyy') +' \n\n ' + data.deName );
-		  
-            field.focus();
-
-            return;
-        }
-    }
-	
-	var dueDate = new Date( jQuery('#dueDate').val() );
-	var inputtedDate = new Date( fieldValue );
-	if( inputtedDate < dueDate )
-	{
-		field.css({
-                "background-color":"#ffcc00"
-            });
-            window.alert( i18n_date_is_greater_then_or_equals_due_date );
-		  
-            field.focus();
-
-            return;
-	}
 	
     var dateSaver = new DateSaver( dataElementId, fieldValue, providedByAnotherFacility, '#ccffcc' );
     dateSaver.save();

=== modified file 'dhis-2/dhis-web/dhis-web-caseentry/src/main/webapp/dhis-web-caseentry/validationResult.vm'
--- dhis-2/dhis-web/dhis-web-caseentry/src/main/webapp/dhis-web-caseentry/validationResult.vm	2011-10-03 08:54:51 +0000
+++ dhis-2/dhis-web/dhis-web-caseentry/src/main/webapp/dhis-web-caseentry/validationResult.vm	2012-01-13 02:14:28 +0000
@@ -8,12 +8,16 @@
 	<p class="bold">$encoder.htmlEncode( $i18n.getString( "the_following_dataelements_are_in_multi_stages" ) )</p>
 	<table class="listTable" style="width:100%">
 		<tr>
-			<th>$i18n.getString( "program_validation_description" )</th>
+			<th>$i18n.getString( "description" )</th>
+			<th>$i18n.getString( "leftSide" )</th>
+			<th>$i18n.getString( "rightSide" )</th>
 		</tr>
 		#set( $mark = false )	    
 		#foreach( $programValidation in $programValidations ) 
-			<tr>	    
-				<td style="height:32px"#alternate( $mark )>$programValidation.description</td>	        
+			<tr #alternate( $mark )>	    
+				<td>$programValidation.description</td>
+				<td>$leftsideFormulaMap.get( $programValidation.id )</td>
+				<td style="height:32px">$rightsideFormulaMap.get( $programValidation.id )</td>	        
 			</tr>
 			#set( $mark = !$mark )
 		#end

=== modified file 'dhis-2/dhis-web/dhis-web-maintenance/dhis-web-maintenance-patient/src/main/java/org/hisp/dhis/patient/action/validation/AddProgramValidationAction.java'
--- dhis-2/dhis-web/dhis-web-maintenance/dhis-web-maintenance-patient/src/main/java/org/hisp/dhis/patient/action/validation/AddProgramValidationAction.java	2012-01-11 05:31:53 +0000
+++ dhis-2/dhis-web/dhis-web-maintenance/dhis-web-maintenance-patient/src/main/java/org/hisp/dhis/patient/action/validation/AddProgramValidationAction.java	2012-01-13 02:14:28 +0000
@@ -50,7 +50,7 @@
     private ProgramService programService;
 
     // -------------------------------------------------------------------------
-    // Input
+    // Input/Output
     // -------------------------------------------------------------------------
 
     private String description;
@@ -61,15 +61,24 @@
 
     private Integer programId;
 
+    private Boolean dateType;
+
+    private String message;
+
     // -------------------------------------------------------------------------
     // Setters
     // -------------------------------------------------------------------------
-    
+
     public void setProgramService( ProgramService programService )
     {
         this.programService = programService;
     }
 
+    public void setDateType( Boolean dateType )
+    {
+        this.dateType = dateType;
+    }
+
     public void setProgramValidationService( ProgramValidationService programValidationService )
     {
         this.programValidationService = programValidationService;
@@ -85,6 +94,11 @@
         this.leftSide = leftSide;
     }
 
+    public String getMessage()
+    {
+        return message;
+    }
+
     public void setRightSide( String rightSide )
     {
         this.rightSide = rightSide;
@@ -113,11 +127,12 @@
         validation.setDescription( description.trim() );
         validation.setLeftSide( leftSide.trim() );
         validation.setRightSide( rightSide.trim() );
+        validation.setDateType( dateType );
 
         Program program = programService.getProgram( programId );
         validation.setProgram( program );
 
-        programValidationService.addProgramValidation( validation );
+        message = programValidationService.addProgramValidation( validation ) + "";
 
         return SUCCESS;
     }

=== added file 'dhis-2/dhis-web/dhis-web-maintenance/dhis-web-maintenance-patient/src/main/java/org/hisp/dhis/patient/action/validation/GetDateDataElementsAction.java'
--- dhis-2/dhis-web/dhis-web-maintenance/dhis-web-maintenance-patient/src/main/java/org/hisp/dhis/patient/action/validation/GetDateDataElementsAction.java	1970-01-01 00:00:00 +0000
+++ dhis-2/dhis-web/dhis-web-maintenance/dhis-web-maintenance-patient/src/main/java/org/hisp/dhis/patient/action/validation/GetDateDataElementsAction.java	2012-01-13 02:14:28 +0000
@@ -0,0 +1,164 @@
+/*
+ * Copyright (c) 2004-2012, University of Oslo
+ * All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions are met:
+ * * Redistributions of source code must retain the above copyright notice, this
+ *   list of conditions and the following disclaimer.
+ * * Redistributions in binary form must reproduce the above copyright notice,
+ *   this list of conditions and the following disclaimer in the documentation
+ *   and/or other materials provided with the distribution.
+ * * Neither the name of the HISP project nor the names of its contributors may
+ *   be used to endorse or promote products derived from this software without
+ *   specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" AND
+ * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
+ * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
+ * DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR
+ * ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
+ * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
+ * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON
+ * ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
+ * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+package org.hisp.dhis.patient.action.validation;
+
+import java.util.ArrayList;
+import java.util.Collection;
+import java.util.HashMap;
+import java.util.Iterator;
+import java.util.List;
+import java.util.Map;
+
+import org.hisp.dhis.dataelement.DataElement;
+import org.hisp.dhis.dataelement.DataElementCategoryService;
+import org.hisp.dhis.program.ProgramStageDataElement;
+import org.hisp.dhis.program.ProgramStageService;
+import org.hisp.dhis.program.ProgramValidation;
+import org.hisp.dhis.program.ProgramValidationService;
+
+import com.opensymphony.xwork2.Action;
+
+/**
+ * @author Chau Thu Tran
+ * 
+ * @version $GetDateDataElementsAction.java Jan 12, 2012 10:30:44 PM$
+ */
+public class GetDateDataElementsAction
+    implements Action
+{
+    // -------------------------------------------------------------------------
+    // Dependencies
+    // -------------------------------------------------------------------------
+
+    private ProgramStageService programStageService;
+
+    public void setProgramStageService( ProgramStageService programStageService )
+    {
+        this.programStageService = programStageService;
+    }
+
+//    private ProgramStageDataElementService programStageDataElementService;
+//
+//    public void setProgramStageDataElementService( ProgramStageDataElementService programStageDataElementService )
+//    {
+//        this.programStageDataElementService = programStageDataElementService;
+//    }
+    
+    private DataElementCategoryService categoryService;
+
+    public void setCategoryService( DataElementCategoryService categoryService )
+    {
+        this.categoryService = categoryService;
+    }
+
+    private ProgramValidationService programValidationService;
+
+    public void setProgramValidationService( ProgramValidationService programValidationService )
+    {
+        this.programValidationService = programValidationService;
+    }
+
+    // -------------------------------------------------------------------------
+    // Input & Output
+    // -------------------------------------------------------------------------
+
+    private Integer psId;
+
+    public void setPsId( Integer psId )
+    {
+        this.psId = psId;
+    }
+
+    public Integer getPsId()
+    {
+        return psId;
+    }
+
+    private int optionComboId;
+
+    public int getOptionComboId()
+    {
+        return optionComboId;
+    }
+
+    private List<DataElement> dataElementList = new ArrayList<DataElement>();
+
+    public List<DataElement> getDataElementList()
+    {
+        return dataElementList;
+    }
+
+    private Map<Integer, ProgramValidation> validationMap = new HashMap<Integer, ProgramValidation>();
+
+    public Map<Integer, ProgramValidation> getValidationMap()
+    {
+        return validationMap;
+    }
+
+    // -------------------------------------------------------------------------
+    // Action implementation
+    // -------------------------------------------------------------------------
+
+    public String execute()
+    {
+        Collection<ProgramStageDataElement> psDataElements = programStageService.getProgramStage( psId ).getProgramStageDataElements();
+        
+        if ( psDataElements != null && !psDataElements.isEmpty() )
+        {
+            optionComboId = categoryService.getDefaultDataElementCategoryOptionCombo().getId();
+           
+            Iterator<ProgramStageDataElement> iter = psDataElements.iterator();
+
+            while ( iter.hasNext() )
+            {
+                ProgramStageDataElement psDe = iter.next();
+
+                DataElement de = psDe.getDataElement();
+                
+                if ( de.getType().equals( DataElement.VALUE_TYPE_DATE ) )
+                {
+                    dataElementList.add( de );
+                    
+                    Collection<ProgramValidation> validation = programValidationService.getProgramValidation( psDe );
+                
+                    if( !validation.isEmpty() )
+                    {
+                        validationMap.put( de.getId(), validation.iterator().next() );
+                    }
+                    else
+                    {
+                        validationMap.put( de.getId(), null );
+                    }
+                }
+            }
+        }
+
+        return SUCCESS;
+    }
+
+}

=== modified file 'dhis-2/dhis-web/dhis-web-maintenance/dhis-web-maintenance-patient/src/main/java/org/hisp/dhis/patient/action/validation/GetProgramValidationListAction.java'
--- dhis-2/dhis-web/dhis-web-maintenance/dhis-web-maintenance-patient/src/main/java/org/hisp/dhis/patient/action/validation/GetProgramValidationListAction.java	2012-01-11 05:31:53 +0000
+++ dhis-2/dhis-web/dhis-web-maintenance/dhis-web-maintenance-patient/src/main/java/org/hisp/dhis/patient/action/validation/GetProgramValidationListAction.java	2012-01-13 02:14:28 +0000
@@ -99,7 +99,7 @@
     {
         Program program = programService.getProgram( programId );
 
-        validations = programValidationService.getProgramValidation( program );
+        validations = programValidationService.getProgramValidation( program, false );
 
         return SUCCESS;
     }

=== modified file 'dhis-2/dhis-web/dhis-web-maintenance/dhis-web-maintenance-patient/src/main/resources/META-INF/dhis/beans.xml'
--- dhis-2/dhis-web/dhis-web-maintenance/dhis-web-maintenance-patient/src/main/resources/META-INF/dhis/beans.xml	2012-01-11 05:31:53 +0000
+++ dhis-2/dhis-web/dhis-web-maintenance/dhis-web-maintenance-patient/src/main/resources/META-INF/dhis/beans.xml	2012-01-13 02:14:28 +0000
@@ -863,6 +863,19 @@
 			<ref bean="org.hisp.dhis.program.ProgramValidationService" />
 		</property>
 	</bean>
+	
+	<bean
+		id="org.hisp.dhis.patient.action.validation.GetDateDataElementsAction"
+		class="org.hisp.dhis.patient.action.validation.GetDateDataElementsAction"
+		scope="prototype">
+		<property name="programStageService">
+			<ref bean="org.hisp.dhis.program.ProgramStageService" />
+		</property>
+		<property name="categoryService"
+			ref="org.hisp.dhis.dataelement.DataElementCategoryService" />
+		<property name="programValidationService"
+			ref="org.hisp.dhis.program.ProgramValidationService" />
+	</bean>
 
 	<!-- Configuration -->
 

=== modified file 'dhis-2/dhis-web/dhis-web-maintenance/dhis-web-maintenance-patient/src/main/resources/org/hisp/dhis/patient/i18n_module.properties'
--- dhis-2/dhis-web/dhis-web-maintenance/dhis-web-maintenance-patient/src/main/resources/org/hisp/dhis/patient/i18n_module.properties	2012-01-11 07:31:29 +0000
+++ dhis-2/dhis-web/dhis-web-maintenance/dhis-web-maintenance-patient/src/main/resources/org/hisp/dhis/patient/i18n_module.properties	2012-01-13 02:14:28 +0000
@@ -388,4 +388,16 @@
 edit_program_validation = Edit program validation 
 age = Age
 birthDate = Birthdate
-assign_validation_for_programs = Assign validation for programs
\ No newline at end of file
+assign_validation_for_programs = Assign validation for programs
+validation_for_date_data_elements = Validation for date date elements
+before_current_date = Before current date
+before_or_equals_to_current_date = Before or equals to current date
+after_current_date = After current date
+after_or_equals_to_current_date = After or equals to current date
+before_due_date = Before due date
+before_or_equals_to_due_date = Before or equals to due date
+after_due_date = After due date
+after_or_equals_to_due_date = After or equals to due date
+data_element = Data element
+condition = Condition
+no_date_data_element_in_selected_program_stage = No data elements with date-type in the selected program stage
\ No newline at end of file

=== modified file 'dhis-2/dhis-web/dhis-web-maintenance/dhis-web-maintenance-patient/src/main/resources/struts.xml'
--- dhis-2/dhis-web/dhis-web-maintenance/dhis-web-maintenance-patient/src/main/resources/struts.xml	2011-12-22 02:47:09 +0000
+++ dhis-2/dhis-web/dhis-web-maintenance/dhis-web-maintenance-patient/src/main/resources/struts.xml	2012-01-13 02:14:28 +0000
@@ -867,6 +867,15 @@
 			<param name="javascripts">javascript/programValidation.js</param>
 			<param name="requiredAuthorities">F_PROGRAM_VALIDATION</param>
 		</action>
+		
+		<action name="defineDateProgramValidationForm"
+			class="org.hisp.dhis.patient.action.program.GetProgramAction">
+			<result name="success" type="velocity">/main.vm</result>
+			<param name="page">/dhis-web-maintenance-patient/addDateProgramValidationForm.vm</param>
+			<param name="menu">/dhis-web-maintenance-patient/patientAndProgramMenu.vm</param>
+			<param name="javascripts">javascript/programValidation.js</param>
+			<param name="requiredAuthorities">F_PROGRAM_VALIDATION</param>
+		</action>
 
 		<action name="addProgramValidation"
 			class="org.hisp.dhis.patient.action.validation.AddProgramValidationAction">
@@ -913,6 +922,26 @@
 				/dhis-web-commons/ajax/jsonProgramValidation.vm</result>
 			<param name="onExceptionReturn">plainTextError</param>
 		</action>
+		
+		<action name="getDateDataElements"
+			class="org.hisp.dhis.patient.action.validation.GetDateDataElementsAction">
+			<result name="success" type="velocity">/content.vm</result>
+			<param name="page">/dhis-web-maintenance-patient/dateProgramValidationForm.vm</param>
+		</action>
+		
+		<action name="addDateProgramValidation"
+			class="org.hisp.dhis.patient.action.validation.AddProgramValidationAction">
+			<result name="success" type="velocity-json">
+				/dhis-web-commons/ajax/jsonResponseSuccess.vm</result>
+			<param name="requiredAuthorities">F_PROGRAM_VALIDATION</param>
+		</action>
+		
+		<action name="updateDateProgramValidation"
+			class="org.hisp.dhis.patient.action.validation.UpdateProgramValidationAction">
+			<result name="success" type="velocity-json">
+				/dhis-web-commons/ajax/jsonResponseSuccess.vm</result>
+			<param name="requiredAuthorities">F_PROGRAM_VALIDATION</param>
+		</action>
 
 		<!-- Configuration -->
 

=== added file 'dhis-2/dhis-web/dhis-web-maintenance/dhis-web-maintenance-patient/src/main/webapp/dhis-web-maintenance-patient/addDateProgramValidationForm.vm'
--- dhis-2/dhis-web/dhis-web-maintenance/dhis-web-maintenance-patient/src/main/webapp/dhis-web-maintenance-patient/addDateProgramValidationForm.vm	1970-01-01 00:00:00 +0000
+++ dhis-2/dhis-web/dhis-web-maintenance/dhis-web-maintenance-patient/src/main/webapp/dhis-web-maintenance-patient/addDateProgramValidationForm.vm	2012-01-13 02:14:28 +0000
@@ -0,0 +1,35 @@
+<h3>$i18n.getString( "validation_for_date_data_elements" )</h3>
+
+<form id='programValidationForm' name='programValidationForm' method='post' action='addProgramValidation.action'>
+
+<input type='hidden' id='programId' name='programId' value='$program.id'>
+<input type='hidden' id='dateType' name='dateType' value='true'>
+<table>
+	<tr>
+		<th colspan='3'>
+			<label>$i18n.getString('program_stage')</label>
+		</th>
+	</tr>
+	<tr>
+		<td colspan='3'>
+			<select style="width:630px" id='programStage' name='programStage' onchange="getDateDataElements();">
+				<option value=''>[$i18n.getString( "please_select" )]</option>
+				#foreach($stage in $program.programStages)
+				<option value='$stage.id'>$stage.name</option>
+				#end
+			</select>
+		</td>
+	</tr>
+	<tbody id='dataElementValidation'></tbody>
+	<tr>
+		<td colspan='3'>
+			#parse( "dhis-web-commons/loader/loader.vm" )
+		</td>
+	<tr>
+	<tr>
+		<td>
+			<input type='button' value="$i18n.getString( "cancel" )" style="width:10em" onclick="window.location.href='programValidation.action?programId=$program.id'">
+		</td>
+		<td></td>
+	</tr>
+</table>

=== modified file 'dhis-2/dhis-web/dhis-web-maintenance/dhis-web-maintenance-patient/src/main/webapp/dhis-web-maintenance-patient/addMultiProgramValidationForm.vm'
--- dhis-2/dhis-web/dhis-web-maintenance/dhis-web-maintenance-patient/src/main/webapp/dhis-web-maintenance-patient/addMultiProgramValidationForm.vm	2011-07-08 05:52:59 +0000
+++ dhis-2/dhis-web/dhis-web-maintenance/dhis-web-maintenance-patient/src/main/webapp/dhis-web-maintenance-patient/addMultiProgramValidationForm.vm	2012-01-13 02:14:28 +0000
@@ -1,9 +1,9 @@
-<script type="text/javascript" src="javascript/addProgramValidationForm.js"></script>
 <h3>$i18n.getString( "add_multi_program_validation" )</h3>
 
 <form id='programValidationForm' name='programValidationForm' method='post' action='addProgramValidation.action'>
 
 <input type='hidden' id='programId' name='programId' value='$program.id'>
+<input type='hidden' id='dateType' name='dateType' value='false'>
 <table>
 	
 	<thead>
@@ -24,6 +24,11 @@
 		</td>
 	</tr>
 	<tr>
+		<th colspan='2'>
+			<label>$i18n.getString('validation')</label>
+		</th>
+	</tr>
+	<tr>
 		<td width="20em">
 			<label>$i18n.getString('left_side')</label>
 		</td>

=== modified file 'dhis-2/dhis-web/dhis-web-maintenance/dhis-web-maintenance-patient/src/main/webapp/dhis-web-maintenance-patient/addSingleProgramValidationForm.vm'
--- dhis-2/dhis-web/dhis-web-maintenance/dhis-web-maintenance-patient/src/main/webapp/dhis-web-maintenance-patient/addSingleProgramValidationForm.vm	2011-07-08 05:52:59 +0000
+++ dhis-2/dhis-web/dhis-web-maintenance/dhis-web-maintenance-patient/src/main/webapp/dhis-web-maintenance-patient/addSingleProgramValidationForm.vm	2012-01-13 02:14:28 +0000
@@ -1,9 +1,9 @@
-<script type="text/javascript" src="javascript/addProgramValidationForm.js"></script>
 <h3>$i18n.getString( "add_single_program_validation" )</h3>
 
 <form id='programValidationForm' name='programValidationForm' method='post' action='addProgramValidation.action'>
 
 <input type='hidden' id='programId' name='programId' value='$program.id'>
+<input type='hidden' id='dateType' name='dateType' value='false'>
 <table>
 	
 	<thead>
@@ -24,9 +24,9 @@
 		</td>
 	</tr>
 	<tr>
-		<td>
+		<th>
 			<label>$i18n.getString('validation')</label>
-		</td>
+		</th>
 	</tr>
 	<tr>
 		<td>

=== added file 'dhis-2/dhis-web/dhis-web-maintenance/dhis-web-maintenance-patient/src/main/webapp/dhis-web-maintenance-patient/dateProgramValidationForm.vm'
--- dhis-2/dhis-web/dhis-web-maintenance/dhis-web-maintenance-patient/src/main/webapp/dhis-web-maintenance-patient/dateProgramValidationForm.vm	1970-01-01 00:00:00 +0000
+++ dhis-2/dhis-web/dhis-web-maintenance/dhis-web-maintenance-patient/src/main/webapp/dhis-web-maintenance-patient/dateProgramValidationForm.vm	2012-01-13 02:14:28 +0000
@@ -0,0 +1,43 @@
+<table>
+#if( $dataElementList.size() > 0 )
+	<col width="30"/>
+    <col width="400"/>
+    <col/>
+	
+	<tr>
+		<th>$i18n.getString('#')</th>
+		<th>$i18n.getString('data_element')</th>
+		<th>$i18n.getString('condition')</th>
+	</tr>	
+
+	#set( $mark = false )
+	#set( $index = 0 )
+	#foreach( $dataElement in $dataElementList )
+		#set( $id= '[DE:' + $psId + '.' + $dataElement.id + '.' + $optionComboId + ']')
+		#set( $validationId= $id + '.validation' )
+		#set( $index = $index + 1 )
+		<tr #alternate($mark) >
+			<td>$index</td>
+			<td>$dataElement.name</td>
+			<td> 
+				<select id="$dataElement.id" validationid="$!validationMap.get($dataElement.id).id" onchange="addDateValidation('$id','$dataElement.id' ,'$dataElement.name' )" >
+					<option value='' selected>[$i18n.getString('please_select')] </option>
+					<option value='1' #if( $!validationMap.get($dataElement.id).rightSide=='1' ) selected #end >$i18n.getString('before_current_date') </option>
+					<option value='3' #if( $!validationMap.get($dataElement.id).rightSide=='3' ) selected #end >$i18n.getString('after_current_date') </option>
+					<option value='2' #if( $!validationMap.get($dataElement.id).rightSide=='2' ) selected #end >$i18n.getString('before_or_equals_to_current_date') </option>
+					<option value='4' #if( $!validationMap.get($dataElement.id).rightSide=='4' ) selected #end >$i18n.getString('after_or_equals_to_current_date') </option>
+					<option value='-1' #if( $!validationMap.get($dataElement.id).rightSide=='-1' ) selected #end >$i18n.getString('before_due_date') </option>
+					<option value='-3' #if( $!validationMap.get($dataElement.id).rightSide=='-3' ) selected #end >$i18n.getString('after_due_date') </option>
+					<option value='-2' #if( $!validationMap.get($dataElement.id).rightSide=='-2' ) selected #end >$i18n.getString('before_or_equals_to_due_date') </option>
+					<option value='-4' #if( $!validationMap.get($dataElement.id).rightSide=='' ) selected #end >$i18n.getString('after_or_equals_to_due_date') </option>
+				</select>
+			</td>
+		</tr>
+		#set ( $mark = !$mark)
+	#end
+#else
+	<tr>
+		<td colspan='2'>$i18n.getString('no_date_data_element_in_selected_program_stage')<td>
+	</tr>
+#end
+</table>
\ No newline at end of file

=== modified file 'dhis-2/dhis-web/dhis-web-maintenance/dhis-web-maintenance-patient/src/main/webapp/dhis-web-maintenance-patient/javascript/programValidation.js'
--- dhis-2/dhis-web/dhis-web-maintenance/dhis-web-maintenance-patient/src/main/webapp/dhis-web-maintenance-patient/javascript/programValidation.js	2012-01-11 07:42:49 +0000
+++ dhis-2/dhis-web/dhis-web-maintenance/dhis-web-maintenance-patient/src/main/webapp/dhis-web-maintenance-patient/javascript/programValidation.js	2012-01-13 02:14:28 +0000
@@ -1,4 +1,6 @@
 
+var COLOR_GREEN = '#b9ffb9';
+
 jQuery(document).ready(	function(){
 	validation( 'programValidationForm', function( form ){			
 		form.submit();
@@ -159,3 +161,76 @@
 		programstageDE.add(option, null); 
 	});
 }
+
+function getDateDataElements()
+{
+	hideById('dataElementValidation');
+	showLoader();
+	var programStageId = getFieldValue('programStage');
+	
+	if( programStageId == '')
+	{
+		hideById('loaderDiv');
+		hideById('dataElementValidation');
+		return;
+	}
+	
+	$( '#dataElementValidation' ).load( "getDateDataElements.action", 
+		{ 
+			psId:programStageId
+		},function( )
+		{	
+			hideById('loaderDiv');
+			showById('dataElementValidation');
+		});
+}
+
+function addDateValidation( id, fieldId, dataElementName )
+{
+	var expression = $("#" + fieldId + ' option:selected').val();
+	var validationid = $("#" + fieldId ).attr('validationid');
+	
+	if( validationid == '')
+	{
+		var description =  $('#programStage option:selected').text() + ' - ' + dataElementName;
+		jQuery.post( "addDateProgramValidation.action", {
+			description: description,
+			leftSide: id,
+			rightSide: expression,
+			programId: getFieldValue('programId'),
+			dateType: getFieldValue('dateType')
+		}, function( json )
+		{
+			byId( fieldId ).style.backgroundColor = COLOR_GREEN;
+			$("#" + fieldId ).attr('validationid', json.message );
+		});
+	}
+	else
+	{
+		var rightSide = $("#" + fieldId + ' option:selected').val();
+		if( rightSide == '')
+		{
+			jQuery.post( "removeProgramValidation.action", {
+				id:validationid
+			}, function( json )
+			{
+				byId( fieldId ).style.backgroundColor = COLOR_GREEN;
+				$("#" + fieldId ).attr('validationid', '' );
+			});
+		}
+		else
+		{
+			var description =  $('#programStage option:selected').text() + ' - ' + dataElementName;
+			jQuery.post( "updateDateProgramValidation.action", {
+				id:validationid,
+				description: description,
+				leftSide: id,
+				rightSide: expression,
+				programId: getFieldValue('programId')
+			}, function( json )
+			{
+				byId( fieldId ).style.backgroundColor = COLOR_GREEN;
+			});
+		}
+	}
+}

=== modified file 'dhis-2/dhis-web/dhis-web-maintenance/dhis-web-maintenance-patient/src/main/webapp/dhis-web-maintenance-patient/programValidationList.vm'
--- dhis-2/dhis-web/dhis-web-maintenance/dhis-web-maintenance-patient/src/main/webapp/dhis-web-maintenance-patient/programValidationList.vm	2012-01-11 07:42:49 +0000
+++ dhis-2/dhis-web/dhis-web-maintenance/dhis-web-maintenance-patient/src/main/webapp/dhis-web-maintenance-patient/programValidationList.vm	2012-01-13 02:14:28 +0000
@@ -20,6 +20,12 @@
 			  </tr>
 
 			  <tbody id="list">
+				<tr id="tr${validation.id}">
+					<td>$i18n.getString( "validation_for_date_data_elements" )</td>
+					<td>
+					  <a href="defineDateProgramValidationForm.action?id=$programId" title="$i18n.getString( "edit" )"><img src="../images/edit.png" alt="$i18n.getString( 'edit' )"></a>						
+					</td>
+				</tr>
 				#foreach( $validation in $validations )
 				  <tr id="tr${validation.id}">
 					
@@ -45,8 +51,8 @@
 
 			<div id="detailsArea" style="display:none">
 				<div style="float:right">
-					<a href="javascript:hideDetails()" title="$i18n.getString( "hide_details" )"><img src="../images/close.png" alt="$i18n.getString( "hide_details" )"></a>
-				</div>				
+					<a href="javascript:hideDetails()" title="$i18n.getString( 'hide_details' )"><img src="../images/close.png" alt="$i18n.getString( 'hide_details' )"></a>
+				</div>			
 				<p><label class="bold">$i18n.getString( "name" ):</label><br><span id="descriptionField"></span></p>
 				<p><label class="bold" id='leftSideTitle'>$i18n.getString( "left_side" ):</label><br><span id="leftSideField"></span></p>
 				<p id='rightSideDiv'><label class="bold">$i18n.getString( "right_side" ):</label><br><span id="rightSideField"></span></p>