← Back to team overview

dhis2-devs team mailing list archive

[Branch ~dhis2-devs-core/dhis2/trunk] Rev 13539: Data entry, implemented locking of forms when approved

 

------------------------------------------------------------
revno: 13539
committer: Lars Helge Øverland <larshelge@xxxxxxxxx>
branch nick: dhis2
timestamp: Thu 2014-01-02 14:36:45 +0100
message:
  Data entry, implemented locking of forms when approved
modified:
  dhis-2/dhis-api/src/main/java/org/hisp/dhis/dataapproval/DataApprovalService.java
  dhis-2/dhis-api/src/main/java/org/hisp/dhis/dataset/DataSetService.java
  dhis-2/dhis-services/dhis-service-core/src/main/java/org/hisp/dhis/dataapproval/DefaultDataApprovalService.java
  dhis-2/dhis-services/dhis-service-core/src/main/java/org/hisp/dhis/dataset/DefaultDataSetService.java
  dhis-2/dhis-services/dhis-service-core/src/main/java/org/hisp/dhis/sms/DataValueSMSListener.java
  dhis-2/dhis-services/dhis-service-core/src/main/resources/META-INF/dhis/beans.xml
  dhis-2/dhis-services/dhis-service-core/src/test/java/org/hisp/dhis/dataset/DataSetServiceTest.java
  dhis-2/dhis-web/dhis-web-api/src/main/java/org/hisp/dhis/api/utils/ContextUtils.java
  dhis-2/dhis-web/dhis-web-api/src/main/java/org/hisp/dhis/api/utils/InputUtils.java
  dhis-2/dhis-web/dhis-web-api/src/main/resources/META-INF/dhis/beans.xml
  dhis-2/dhis-web/dhis-web-dataentry/pom.xml
  dhis-2/dhis-web/dhis-web-dataentry/src/main/java/org/hisp/dhis/de/action/GetDataValuesForDataSetAction.java
  dhis-2/dhis-web/dhis-web-dataentry/src/main/java/org/hisp/dhis/de/action/RegisterCompleteDataSetAction.java
  dhis-2/dhis-web/dhis-web-dataentry/src/main/java/org/hisp/dhis/de/action/UndoCompleteDataSetAction.java
  dhis-2/dhis-web/dhis-web-dataentry/src/main/resources/META-INF/dhis/beans.xml
  dhis-2/dhis-web/dhis-web-dataentry/src/main/webapp/dhis-web-dataentry/javascript/form.js
  dhis-2/dhis-web/dhis-web-light/src/main/java/org/hisp/dhis/light/dataentry/action/GetPeriodsAction.java


--
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/dataapproval/DataApprovalService.java'
--- dhis-2/dhis-api/src/main/java/org/hisp/dhis/dataapproval/DataApprovalService.java	2013-12-27 12:17:16 +0000
+++ dhis-2/dhis-api/src/main/java/org/hisp/dhis/dataapproval/DataApprovalService.java	2014-01-02 13:36:45 +0000
@@ -59,7 +59,8 @@
 
     /**
      * Returns the DataApproval object (if any) for a given
-     * dataset, period and organisation unit.
+     * dataset, period and organisation unit. If attributeOptionCombo is null,
+     * the default option combo will be used.
      *
      * @param dataSet DataSet for approval
      * @param period Period for approval
@@ -72,7 +73,8 @@
     
     /**
      * Returns the DataApprovalState for a given data set, period and
-     * OrganisationUnit.
+     * OrganisationUnit. If attributeOptionCombo is null, the default option 
+     * combo will be used.
      *
      * @param dataSet DataSet to check for approval.
      * @param period Period to check for approval.

=== modified file 'dhis-2/dhis-api/src/main/java/org/hisp/dhis/dataset/DataSetService.java'
--- dhis-2/dhis-api/src/main/java/org/hisp/dhis/dataset/DataSetService.java	2013-12-15 22:20:57 +0000
+++ dhis-2/dhis-api/src/main/java/org/hisp/dhis/dataset/DataSetService.java	2014-01-02 13:36:45 +0000
@@ -29,6 +29,7 @@
  */
 
 import org.hisp.dhis.dataelement.DataElement;
+import org.hisp.dhis.dataelement.DataElementCategoryOptionCombo;
 import org.hisp.dhis.organisationunit.OrganisationUnit;
 import org.hisp.dhis.period.Period;
 import org.hisp.dhis.period.PeriodType;
@@ -348,33 +349,36 @@
     /**
      * Checks whether the system is locked for data entry for the given input.
      *
-     * @param dataSet          the data set
-     * @param period           Period the period.s
+     * @param dataSet the data set
+     * @param period the period.
      * @param organisationUnit the organisation unit.
-     * @param now              the base date for deciding locked date, current date if null.
+     * @param attributeOptionCombo the attribute option combo.
+     * @param now the base date for deciding locked date, current date if null.
      * @return true or false indicating whether the system is locked or not.
      */
-    boolean isLocked( DataSet dataSet, Period period, OrganisationUnit organisationUnit, Date now );
+    boolean isLocked( DataSet dataSet, Period period, OrganisationUnit organisationUnit, DataElementCategoryOptionCombo attributeOptionCombo, Date now );
 
     /**
      * Checks whether the system is locked for data entry for the given input.
+     * The status u
      *
-     * @param dataSet            the data set
-     * @param period             Period the period.s
-     * @param organisationUnit   the organisation unit.
-     * @param now                the base date for deciding locked date, current date if null.
+     * @param dataSet the data set
+     * @param period the period.
+     * @param organisationUnit the organisation unit.
+     * @param attributeOptionCombo the attribute option combo.
+     * @param now the base date for deciding locked date, current date if null.
      * @param useOrgUnitChildren whether to check children of the given org unit or the org unit only.
      * @return true or false indicating whether the system is locked or not.
      */
-    boolean isLocked( DataSet dataSet, Period period, OrganisationUnit organisationUnit, Date now, boolean useOrgUnitChildren );
+    boolean isLocked( DataSet dataSet, Period period, OrganisationUnit organisationUnit, DataElementCategoryOptionCombo attributeOptionCombo, Date now, boolean useOrgUnitChildren );
 
     /**
      * Checks whether the system is locked for data entry for the given input.
      *
-     * @param dataElement      the data element.
-     * @param period           the period.
+     * @param dataElement the data element.
+     * @param period the period.
      * @param organisationUnit the organisation unit.
-     * @param now              the base date for deciding locked date, current date if null.
+     * @param now the base date for deciding locked date, current date if null.
      * @return true or false indicating whether the system is locked or not.
      */
     boolean isLocked( DataElement dataElement, Period period, OrganisationUnit organisationUnit, Date now );

=== modified file 'dhis-2/dhis-services/dhis-service-core/src/main/java/org/hisp/dhis/dataapproval/DefaultDataApprovalService.java'
--- dhis-2/dhis-services/dhis-service-core/src/main/java/org/hisp/dhis/dataapproval/DefaultDataApprovalService.java	2013-12-27 20:50:53 +0000
+++ dhis-2/dhis-services/dhis-service-core/src/main/java/org/hisp/dhis/dataapproval/DefaultDataApprovalService.java	2014-01-02 13:36:45 +0000
@@ -30,6 +30,7 @@
 
 import org.apache.commons.collections.CollectionUtils;
 import org.hisp.dhis.dataelement.DataElementCategoryOptionCombo;
+import org.hisp.dhis.dataelement.DataElementCategoryService;
 import org.hisp.dhis.dataset.DataSet;
 import org.hisp.dhis.organisationunit.OrganisationUnit;
 import org.hisp.dhis.period.Period;
@@ -61,6 +62,13 @@
     {
         this.currentUserService = currentUserService;
     }
+    
+    private DataElementCategoryService categoryService;
+
+    public void setCategoryService( DataElementCategoryService categoryService )
+    {
+        this.categoryService = categoryService;
+    }
 
     // -------------------------------------------------------------------------
     // DataApproval
@@ -88,16 +96,26 @@
 
     public DataApproval getDataApproval( DataSet dataSet, Period period, OrganisationUnit organisationUnit, DataElementCategoryOptionCombo attributeOptionCombo )
     {
+        if ( attributeOptionCombo == null )
+        {
+            attributeOptionCombo = categoryService.getDefaultDataElementCategoryOptionCombo();
+        }
+        
         return dataApprovalStore.getDataApproval( dataSet, period, organisationUnit, attributeOptionCombo );
     }
 
     public DataApprovalState getDataApprovalState( DataSet dataSet, Period period, OrganisationUnit organisationUnit, DataElementCategoryOptionCombo attributeOptionCombo )
     {
-        if ( ! dataSet.isApproveData() || ! period.getPeriodType().equals( dataSet.getPeriodType() ) )
+        if ( !dataSet.isApproveData() || !period.getPeriodType().equals( dataSet.getPeriodType() ) )
         {
             return DataApprovalState.APPROVAL_NOT_NEEDED;
         }
 
+        if ( attributeOptionCombo == null )
+        {
+            attributeOptionCombo = categoryService.getDefaultDataElementCategoryOptionCombo();
+        }
+        
         if ( null != dataApprovalStore.getDataApproval( dataSet, period, organisationUnit, attributeOptionCombo ) )
         {
             return DataApprovalState.APPROVED;

=== modified file 'dhis-2/dhis-services/dhis-service-core/src/main/java/org/hisp/dhis/dataset/DefaultDataSetService.java'
--- dhis-2/dhis-services/dhis-service-core/src/main/java/org/hisp/dhis/dataset/DefaultDataSetService.java	2013-12-15 22:20:57 +0000
+++ dhis-2/dhis-services/dhis-service-core/src/main/java/org/hisp/dhis/dataset/DefaultDataSetService.java	2014-01-02 13:36:45 +0000
@@ -28,7 +28,23 @@
  * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
  */
 
+import static org.hisp.dhis.i18n.I18nUtils.getCountByName;
+import static org.hisp.dhis.i18n.I18nUtils.getObjectsBetween;
+import static org.hisp.dhis.i18n.I18nUtils.getObjectsBetweenByName;
+import static org.hisp.dhis.i18n.I18nUtils.i18n;
+
+import java.util.ArrayList;
+import java.util.Collection;
+import java.util.Date;
+import java.util.HashSet;
+import java.util.Iterator;
+import java.util.List;
+import java.util.Set;
+
+import org.hisp.dhis.dataapproval.DataApprovalService;
+import org.hisp.dhis.dataapproval.DataApprovalState;
 import org.hisp.dhis.dataelement.DataElement;
+import org.hisp.dhis.dataelement.DataElementCategoryOptionCombo;
 import org.hisp.dhis.dataentryform.DataEntryForm;
 import org.hisp.dhis.i18n.I18nService;
 import org.hisp.dhis.organisationunit.OrganisationUnit;
@@ -39,19 +55,8 @@
 import org.hisp.dhis.system.util.FilterUtils;
 import org.hisp.dhis.user.CurrentUserService;
 import org.joda.time.DateTime;
-import org.springframework.beans.factory.annotation.Autowired;
 import org.springframework.transaction.annotation.Transactional;
 
-import java.util.ArrayList;
-import java.util.Collection;
-import java.util.Date;
-import java.util.HashSet;
-import java.util.Iterator;
-import java.util.List;
-import java.util.Set;
-
-import static org.hisp.dhis.i18n.I18nUtils.*;
-
 /**
  * @author Lars Helge Overland
  * @version $Id: DefaultDataSetService.java 6255 2008-11-10 16:01:24Z larshelg $
@@ -87,7 +92,6 @@
 
     private OrganisationUnitService organisationUnitService;
 
-    @Autowired
     public void setOrganisationUnitService( OrganisationUnitService organisationUnitService )
     {
         this.organisationUnitService = organisationUnitService;
@@ -95,11 +99,17 @@
 
     private CurrentUserService currentUserService;
 
-    @Autowired
     public void setCurrentUserService( CurrentUserService currentUserService )
     {
         this.currentUserService = currentUserService;
     }
+    
+    private DataApprovalService dataApprovalService;
+
+    public void setDataApprovalService( DataApprovalService dataApprovalService )
+    {
+        this.dataApprovalService = dataApprovalService;
+    }
 
     // -------------------------------------------------------------------------
     // DataSet
@@ -447,33 +457,31 @@
     }
 
     @Override
-    public boolean isLocked( DataSet dataSet, Period period, OrganisationUnit organisationUnit, Date now )
+    public boolean isLocked( DataSet dataSet, Period period, OrganisationUnit organisationUnit, DataElementCategoryOptionCombo attributeOptionCombo, Date now )
     {
         now = now != null ? now : new Date();
 
         boolean expired = dataSet.getExpiryDays() != DataSet.NO_EXPIRY && new DateTime( period.getEndDate() ).plusDays( dataSet.getExpiryDays() ).isBefore( new DateTime( now ) );
 
-        return expired && lockExceptionStore.getCount( dataSet, period, organisationUnit ) == 0l;
-    }
-
-    @Override
-    public boolean isLocked( DataElement dataElement, Period period, OrganisationUnit organisationUnit, Date now )
-    {
-        now = now != null ? now : new Date();
-
-        int expiryDays = dataElement.getExpiryDays();
-
-        boolean expired = expiryDays != DataSet.NO_EXPIRY && new DateTime( period.getEndDate() ).plusDays( expiryDays ).isBefore( new DateTime( now ) );
-
-        return expired && lockExceptionStore.getCount( dataElement, period, organisationUnit ) == 0l;
-    }
-
-    @Override
-    public boolean isLocked( DataSet dataSet, Period period, OrganisationUnit organisationUnit, Date now, boolean useOrgUnitChildren )
+        boolean exception = lockExceptionStore.getCount( dataSet, period, organisationUnit ) > 0l;
+        
+        if ( expired && !exception )
+        {
+            return true;
+        }
+        
+        boolean approved = DataApprovalState.APPROVED == dataApprovalService.getDataApprovalState( dataSet, period, organisationUnit, attributeOptionCombo );
+        
+        return approved;
+    }
+
+    @Override
+    public boolean isLocked( DataSet dataSet, Period period, OrganisationUnit organisationUnit, 
+        DataElementCategoryOptionCombo attributeOptionCombo, Date now, boolean useOrgUnitChildren )
     {
         if ( !useOrgUnitChildren )
         {
-            return isLocked( dataSet, period, organisationUnit, now );
+            return isLocked( dataSet, period, organisationUnit, attributeOptionCombo, now );
         }
         
         if ( organisationUnit == null || !organisationUnit.hasChild() )
@@ -483,7 +491,7 @@
         
         for ( OrganisationUnit child : organisationUnit.getChildren() )
         {
-            if ( isLocked( dataSet, period, child, now ) )
+            if ( isLocked( dataSet, period, child, attributeOptionCombo, now ) )
             {
                 return true;
             }
@@ -493,6 +501,18 @@
     }
 
     @Override
+    public boolean isLocked( DataElement dataElement, Period period, OrganisationUnit organisationUnit, Date now )
+    {
+        now = now != null ? now : new Date();
+
+        int expiryDays = dataElement.getExpiryDays();
+
+        boolean expired = expiryDays != DataSet.NO_EXPIRY && new DateTime( period.getEndDate() ).plusDays( expiryDays ).isBefore( new DateTime( now ) );
+
+        return expired && lockExceptionStore.getCount( dataElement, period, organisationUnit ) == 0l;
+    }
+
+    @Override
     public void mergeWithCurrentUserOrganisationUnits( DataSet dataSet, Collection<OrganisationUnit> mergeOrganisationUnits )
     {
         Set<OrganisationUnit> organisationUnits = new HashSet<OrganisationUnit>( dataSet.getSources() );

=== modified file 'dhis-2/dhis-services/dhis-service-core/src/main/java/org/hisp/dhis/sms/DataValueSMSListener.java'
--- dhis-2/dhis-services/dhis-service-core/src/main/java/org/hisp/dhis/sms/DataValueSMSListener.java	2014-01-01 16:19:34 +0000
+++ dhis-2/dhis-services/dhis-service-core/src/main/java/org/hisp/dhis/sms/DataValueSMSListener.java	2014-01-02 13:36:45 +0000
@@ -145,7 +145,7 @@
         OrganisationUnit orgUnit = this.selectOrganisationUnit( orgUnits, parsedMessage );
         Period period = getPeriod( smsCommand, date );
 
-        if ( dataSetService.isLocked( smsCommand.getDataset(), period, orgUnit, null ) )
+        if ( dataSetService.isLocked( smsCommand.getDataset(), period, orgUnit, null, null ) )
         {
             throw new SMSParserException( "Dataset is locked for the period " + period.getStartDate() + " - "
                 + period.getEndDate() );

=== modified file 'dhis-2/dhis-services/dhis-service-core/src/main/resources/META-INF/dhis/beans.xml'
--- dhis-2/dhis-services/dhis-service-core/src/main/resources/META-INF/dhis/beans.xml	2013-12-30 11:14:30 +0000
+++ dhis-2/dhis-services/dhis-service-core/src/main/resources/META-INF/dhis/beans.xml	2014-01-02 13:36:45 +0000
@@ -383,8 +383,9 @@
   </bean>
 
   <bean id="org.hisp.dhis.dataapproval.DataApprovalService" class="org.hisp.dhis.dataapproval.DefaultDataApprovalService">
-      <property name="dataApprovalStore" ref="org.hisp.dhis.dataapproval.DataApprovalStore" />
-      <property name="currentUserService" ref="org.hisp.dhis.user.CurrentUserService" />
+    <property name="dataApprovalStore" ref="org.hisp.dhis.dataapproval.DataApprovalStore" />
+    <property name="currentUserService" ref="org.hisp.dhis.user.CurrentUserService" />
+    <property name="categoryService" ref="org.hisp.dhis.dataelement.DataElementCategoryService" />
   </bean>
 
   <bean id="org.hisp.dhis.dataelement.DataElementService" class="org.hisp.dhis.dataelement.DefaultDataElementService">
@@ -419,6 +420,9 @@
     <property name="dataSetStore" ref="org.hisp.dhis.dataset.DataSetStore" />
     <property name="lockExceptionStore" ref="org.hisp.dhis.dataset.LockExceptionStore" />
     <property name="i18nService" ref="org.hisp.dhis.i18n.I18nService" />
+    <property name="organisationUnitService" ref="org.hisp.dhis.organisationunit.OrganisationUnitService" />
+    <property name="currentUserService" ref="org.hisp.dhis.user.CurrentUserService" />
+    <property name="dataApprovalService" ref="org.hisp.dhis.dataapproval.DataApprovalService" />
   </bean>
 
   <bean id="org.hisp.dhis.dataset.CompleteDataSetRegistrationService"

=== modified file 'dhis-2/dhis-services/dhis-service-core/src/test/java/org/hisp/dhis/dataset/DataSetServiceTest.java'
--- dhis-2/dhis-services/dhis-service-core/src/test/java/org/hisp/dhis/dataset/DataSetServiceTest.java	2013-09-30 11:02:47 +0000
+++ dhis-2/dhis-services/dhis-service-core/src/test/java/org/hisp/dhis/dataset/DataSetServiceTest.java	2014-01-02 13:36:45 +0000
@@ -375,12 +375,12 @@
         // Expiry days
         // ---------------------------------------------------------------------
 
-        assertFalse( dataSetService.isLocked( dataSetA, period, unit, getDate( 2000, 4, 1 ) ) );
-        assertFalse( dataSetService.isLocked( dataSetA, period, unit, getDate( 2000, 4, 5 ) ) );
-        assertTrue( dataSetService.isLocked( dataSetA, period, unit, getDate( 2000, 4, 15 ) ) );
-        assertTrue( dataSetService.isLocked( dataSetA, period, unit, getDate( 2000, 4, 25 ) ) );
-        assertFalse( dataSetService.isLocked( dataSetB, period, unit, getDate( 2000, 4, 10 ) ) );
-        assertTrue( dataSetService.isLocked( dataSetB, period, unit, getDate( 2000, 4, 25 ) ) );
+        assertFalse( dataSetService.isLocked( dataSetA, period, unit, null, getDate( 2000, 4, 1 ) ) );
+        assertFalse( dataSetService.isLocked( dataSetA, period, unit, null, getDate( 2000, 4, 5 ) ) );
+        assertTrue( dataSetService.isLocked( dataSetA, period, unit, null, getDate( 2000, 4, 15 ) ) );
+        assertTrue( dataSetService.isLocked( dataSetA, period, unit, null, getDate( 2000, 4, 25 ) ) );
+        assertFalse( dataSetService.isLocked( dataSetB, period, unit, null, getDate( 2000, 4, 10 ) ) );
+        assertTrue( dataSetService.isLocked( dataSetB, period, unit, null, getDate( 2000, 4, 25 ) ) );
 
         // ---------------------------------------------------------------------
         // Lock exception
@@ -389,11 +389,11 @@
         LockException lockException = new LockException( period, unit, dataSetA );
         dataSetService.addLockException( lockException );
 
-        assertFalse( dataSetService.isLocked( dataSetA, period, unit, getDate( 2000, 4, 1 ) ) );
-        assertFalse( dataSetService.isLocked( dataSetA, period, unit, getDate( 2000, 4, 5 ) ) );
-        assertFalse( dataSetService.isLocked( dataSetA, period, unit, getDate( 2000, 4, 15 ) ) );
-        assertFalse( dataSetService.isLocked( dataSetA, period, unit, getDate( 2000, 4, 25 ) ) );
-        assertFalse( dataSetService.isLocked( dataSetB, period, unit, getDate( 2000, 4, 10 ) ) );
-        assertTrue( dataSetService.isLocked( dataSetB, period, unit, getDate( 2000, 4, 25 ) ) );
+        assertFalse( dataSetService.isLocked( dataSetA, period, unit, null, getDate( 2000, 4, 1 ) ) );
+        assertFalse( dataSetService.isLocked( dataSetA, period, unit, null, getDate( 2000, 4, 5 ) ) );
+        assertFalse( dataSetService.isLocked( dataSetA, period, unit, null, getDate( 2000, 4, 15 ) ) );
+        assertFalse( dataSetService.isLocked( dataSetA, period, unit, null, getDate( 2000, 4, 25 ) ) );
+        assertFalse( dataSetService.isLocked( dataSetB, period, unit, null, getDate( 2000, 4, 10 ) ) );
+        assertTrue( dataSetService.isLocked( dataSetB, period, unit, null, getDate( 2000, 4, 25 ) ) );
     }
 }

=== modified file 'dhis-2/dhis-web/dhis-web-api/src/main/java/org/hisp/dhis/api/utils/ContextUtils.java'
--- dhis-2/dhis-web/dhis-web-api/src/main/java/org/hisp/dhis/api/utils/ContextUtils.java	2013-12-24 15:33:27 +0000
+++ dhis-2/dhis-web/dhis-web-api/src/main/java/org/hisp/dhis/api/utils/ContextUtils.java	2014-01-02 13:36:45 +0000
@@ -28,7 +28,22 @@
  * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
  */
 
+import static org.apache.commons.lang.StringUtils.trimToNull;
+import static org.hisp.dhis.setting.SystemSettingManager.DEFAULT_CACHE_STRATEGY;
+import static org.hisp.dhis.setting.SystemSettingManager.KEY_CACHE_STRATEGY;
+
+import java.io.IOException;
+import java.io.PrintWriter;
+import java.util.ArrayList;
+import java.util.Arrays;
+import java.util.Calendar;
+import java.util.List;
+
 import javassist.util.proxy.ProxyObject;
+
+import javax.servlet.http.HttpServletRequest;
+import javax.servlet.http.HttpServletResponse;
+
 import org.apache.commons.io.IOUtils;
 import org.hisp.dhis.common.BaseDimensionalObject;
 import org.hisp.dhis.common.DimensionalObject;
@@ -39,27 +54,12 @@
 import org.springframework.beans.factory.annotation.Autowired;
 import org.springframework.http.HttpHeaders;
 import org.springframework.security.crypto.codec.Base64;
-import org.springframework.stereotype.Component;
 import org.springframework.web.context.request.RequestContextHolder;
 import org.springframework.web.context.request.ServletRequestAttributes;
 
-import javax.servlet.http.HttpServletRequest;
-import javax.servlet.http.HttpServletResponse;
-import java.io.IOException;
-import java.io.PrintWriter;
-import java.util.ArrayList;
-import java.util.Arrays;
-import java.util.Calendar;
-import java.util.List;
-
-import static org.apache.commons.lang.StringUtils.trimToNull;
-import static org.hisp.dhis.setting.SystemSettingManager.KEY_CACHE_STRATEGY;
-import static org.hisp.dhis.setting.SystemSettingManager.DEFAULT_CACHE_STRATEGY;
-
 /**
  * @author Lars Helge Overland
  */
-@Component
 public class ContextUtils
 {
     public static final String CONTENT_TYPE_PDF = "application/pdf";

=== modified file 'dhis-2/dhis-web/dhis-web-api/src/main/java/org/hisp/dhis/api/utils/InputUtils.java'
--- dhis-2/dhis-web/dhis-web-api/src/main/java/org/hisp/dhis/api/utils/InputUtils.java	2013-12-26 15:31:04 +0000
+++ dhis-2/dhis-web/dhis-web-api/src/main/java/org/hisp/dhis/api/utils/InputUtils.java	2014-01-02 13:36:45 +0000
@@ -11,12 +11,10 @@
 import org.hisp.dhis.dataelement.DataElementCategoryOptionCombo;
 import org.hisp.dhis.dataelement.DataElementCategoryService;
 import org.springframework.beans.factory.annotation.Autowired;
-import org.springframework.stereotype.Component;
 
 /**
  * @author Lars Helge Overland
  */
-@Component
 public class InputUtils
 {
     @Autowired

=== modified file 'dhis-2/dhis-web/dhis-web-api/src/main/resources/META-INF/dhis/beans.xml'
--- dhis-2/dhis-web/dhis-web-api/src/main/resources/META-INF/dhis/beans.xml	2013-09-26 13:17:01 +0000
+++ dhis-2/dhis-web/dhis-web-api/src/main/resources/META-INF/dhis/beans.xml	2014-01-02 13:36:45 +0000
@@ -4,6 +4,7 @@
 	xsi:schemaLocation="http://www.springframework.org/schema/beans http://www.springframework.org/schema/beans/spring-beans-3.2.xsd";>
 	
   <bean id="contextUtils" class="org.hisp.dhis.api.utils.ContextUtils"/>
+  <bean id="inputUtils" class="org.hisp.dhis.api.utils.InputUtils" />
   <bean id="restTemplate" class="org.springframework.web.client.RestTemplate"/>
 
 </beans>

=== modified file 'dhis-2/dhis-web/dhis-web-dataentry/pom.xml'
--- dhis-2/dhis-web/dhis-web-dataentry/pom.xml	2013-12-21 19:02:27 +0000
+++ dhis-2/dhis-web/dhis-web-dataentry/pom.xml	2014-01-02 13:36:45 +0000
@@ -38,7 +38,6 @@
     <dependency>
       <groupId>org.hisp.dhis</groupId>
       <artifactId>dhis-web-api</artifactId>
-      <optional>true</optional>
     </dependency>
     <dependency>
       <groupId>org.hisp.dhis</groupId>
@@ -48,6 +47,10 @@
       <groupId>org.hisp.dhis</groupId>
       <artifactId>dhis-service-reporting</artifactId>
     </dependency>
+    <dependency>
+      <groupId>javax.servlet</groupId>
+      <artifactId>servlet-api</artifactId>
+    </dependency>
         
   </dependencies>
   <properties>

=== modified file 'dhis-2/dhis-web/dhis-web-dataentry/src/main/java/org/hisp/dhis/de/action/GetDataValuesForDataSetAction.java'
--- dhis-2/dhis-web/dhis-web-dataentry/src/main/java/org/hisp/dhis/de/action/GetDataValuesForDataSetAction.java	2013-12-25 15:01:48 +0000
+++ dhis-2/dhis-web/dhis-web-dataentry/src/main/java/org/hisp/dhis/de/action/GetDataValuesForDataSetAction.java	2014-01-02 13:36:45 +0000
@@ -28,15 +28,16 @@
  * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
  */
 
-import com.opensymphony.xwork2.Action;
+import java.util.ArrayList;
+import java.util.Collection;
+import java.util.Date;
+import java.util.Set;
 
 import org.apache.commons.logging.Log;
 import org.apache.commons.logging.LogFactory;
-import org.hisp.dhis.api.utils.ContextUtils;
-import org.hisp.dhis.dataelement.DataElementCategoryCombo;
-import org.hisp.dhis.dataelement.DataElementCategoryOption;
+import org.apache.struts2.ServletActionContext;
+import org.hisp.dhis.api.utils.InputUtils;
 import org.hisp.dhis.dataelement.DataElementCategoryOptionCombo;
-import org.hisp.dhis.dataelement.DataElementCategoryService;
 import org.hisp.dhis.dataset.CompleteDataSetRegistration;
 import org.hisp.dhis.dataset.CompleteDataSetRegistrationService;
 import org.hisp.dhis.dataset.DataSet;
@@ -49,13 +50,9 @@
 import org.hisp.dhis.organisationunit.OrganisationUnitService;
 import org.hisp.dhis.period.Period;
 import org.hisp.dhis.period.PeriodType;
+import org.springframework.beans.factory.annotation.Autowired;
 
-import java.util.ArrayList;
-import java.util.Collection;
-import java.util.Date;
-import java.util.HashSet;
-import java.util.List;
-import java.util.Set;
+import com.opensymphony.xwork2.Action;
 
 /**
  * @author Lars Helge Overland
@@ -104,12 +101,8 @@
         this.organisationUnitService = organisationUnitService;
     }
     
-    private DataElementCategoryService categoryService;
-
-    public void setCategoryService( DataElementCategoryService categoryService )
-    {
-        this.categoryService = categoryService;
-    }
+    @Autowired
+    private InputUtils inputUtils;
 
     // -------------------------------------------------------------------------
     // Input
@@ -214,8 +207,6 @@
 
     public String execute()
     {
-        List<String> opts = ContextUtils.getQueryParamValues( cp );
-        
         // ---------------------------------------------------------------------
         // Validation
         // ---------------------------------------------------------------------
@@ -238,32 +229,7 @@
         // Attributes
         // ---------------------------------------------------------------------
 
-        DataElementCategoryOptionCombo attributeOptionCombo = null;
-        
-        if ( cc != null && opts != null )
-        {
-            DataElementCategoryCombo categoryCombo = categoryService.getDataElementCategoryCombo( cc );
-
-            Set<DataElementCategoryOption> categoryOptions = new HashSet<DataElementCategoryOption>();
-
-            for ( String id : opts )
-            {
-                categoryOptions.add( categoryService.getDataElementCategoryOption( id ) );
-            }
-            
-            attributeOptionCombo = categoryService.getDataElementCategoryOptionCombo( categoryCombo, categoryOptions );
-            
-            if ( attributeOptionCombo == null )
-            {
-                log.warn( "Illegal input, attribute option combo does not exist" );
-                return SUCCESS;
-            }            
-        }
-
-        if ( attributeOptionCombo == null )
-        {
-            attributeOptionCombo = categoryService.getDefaultDataElementCategoryOptionCombo();
-        }
+        DataElementCategoryOptionCombo attributeOptionCombo = inputUtils.getAttributeOptionCombo( ServletActionContext.getResponse(), cc, cp );
         
         // ---------------------------------------------------------------------
         // Data values & Min-max data elements
@@ -304,7 +270,7 @@
                 storedBy = registration.getStoredBy();
             }
 
-            locked = dataSetService.isLocked( dataSet, period, organisationUnit, null );
+            locked = dataSetService.isLocked( dataSet, period, organisationUnit, attributeOptionCombo, null );
         }
         else
         {
@@ -318,7 +284,7 @@
             {
                 if ( ou.getDataSets().contains( dataSet ) )
                 {
-                    locked = dataSetService.isLocked( dataSet, period, organisationUnit, null );
+                    locked = dataSetService.isLocked( dataSet, period, organisationUnit, attributeOptionCombo, null );
 
                     if ( locked )
                     {

=== modified file 'dhis-2/dhis-web/dhis-web-dataentry/src/main/java/org/hisp/dhis/de/action/RegisterCompleteDataSetAction.java'
--- dhis-2/dhis-web/dhis-web-dataentry/src/main/java/org/hisp/dhis/de/action/RegisterCompleteDataSetAction.java	2013-12-15 22:20:57 +0000
+++ dhis-2/dhis-web/dhis-web-dataentry/src/main/java/org/hisp/dhis/de/action/RegisterCompleteDataSetAction.java	2014-01-02 13:36:45 +0000
@@ -31,6 +31,9 @@
 import com.opensymphony.xwork2.Action;
 import org.apache.commons.logging.Log;
 import org.apache.commons.logging.LogFactory;
+import org.apache.struts2.ServletActionContext;
+import org.hisp.dhis.api.utils.InputUtils;
+import org.hisp.dhis.dataelement.DataElementCategoryOptionCombo;
 import org.hisp.dhis.dataset.CompleteDataSetRegistration;
 import org.hisp.dhis.dataset.CompleteDataSetRegistrationService;
 import org.hisp.dhis.dataset.DataSet;
@@ -41,6 +44,7 @@
 import org.hisp.dhis.period.Period;
 import org.hisp.dhis.period.PeriodType;
 import org.hisp.dhis.user.CurrentUserService;
+import org.springframework.beans.factory.annotation.Autowired;
 
 import java.util.Date;
 import java.util.Set;
@@ -92,6 +96,9 @@
         this.format = format;
     }
 
+    @Autowired
+    private InputUtils inputUtils;
+
     // -------------------------------------------------------------------------
     // Input
     // -------------------------------------------------------------------------
@@ -124,6 +131,20 @@
         this.multiOrganisationUnit = multiOrganisationUnit;
     }
 
+    private String cc;
+
+    public void setCc( String cc )
+    {
+        this.cc = cc;
+    }
+
+    private String cp;
+
+    public void setCp( String cp )
+    {
+        this.cp = cp;
+    }
+
     private int statusCode;
 
     public int getStatusCode()
@@ -141,14 +162,16 @@
         Period period = PeriodType.getPeriodFromIsoString( periodId );
         OrganisationUnit organisationUnit = organisationUnitService.getOrganisationUnit( organisationUnitId );
         Set<OrganisationUnit> children = organisationUnit.getChildren();
+        DataElementCategoryOptionCombo attributeOptionCombo = inputUtils.getAttributeOptionCombo( ServletActionContext.getResponse(), cc, cp );
 
         String storedBy = currentUserService.getCurrentUsername();
 
+        
         // ---------------------------------------------------------------------
         // Check locked status
         // ---------------------------------------------------------------------
 
-        if ( dataSetService.isLocked( dataSet, period, organisationUnit, null, multiOrganisationUnit ) )
+        if ( dataSetService.isLocked( dataSet, period, organisationUnit, attributeOptionCombo, null, multiOrganisationUnit ) )
         {
             return logError( "Entry locked: " + dataSet + ", " + period + ", " + organisationUnit, 2 );
         }

=== modified file 'dhis-2/dhis-web/dhis-web-dataentry/src/main/java/org/hisp/dhis/de/action/UndoCompleteDataSetAction.java'
--- dhis-2/dhis-web/dhis-web-dataentry/src/main/java/org/hisp/dhis/de/action/UndoCompleteDataSetAction.java	2013-12-15 22:20:57 +0000
+++ dhis-2/dhis-web/dhis-web-dataentry/src/main/java/org/hisp/dhis/de/action/UndoCompleteDataSetAction.java	2014-01-02 13:36:45 +0000
@@ -31,6 +31,9 @@
 import com.opensymphony.xwork2.Action;
 import org.apache.commons.logging.Log;
 import org.apache.commons.logging.LogFactory;
+import org.apache.struts2.ServletActionContext;
+import org.hisp.dhis.api.utils.InputUtils;
+import org.hisp.dhis.dataelement.DataElementCategoryOptionCombo;
 import org.hisp.dhis.dataset.CompleteDataSetRegistration;
 import org.hisp.dhis.dataset.CompleteDataSetRegistrationService;
 import org.hisp.dhis.dataset.DataSet;
@@ -39,6 +42,7 @@
 import org.hisp.dhis.organisationunit.OrganisationUnitService;
 import org.hisp.dhis.period.Period;
 import org.hisp.dhis.period.PeriodType;
+import org.springframework.beans.factory.annotation.Autowired;
 
 import java.util.Set;
 
@@ -75,6 +79,9 @@
         this.organisationUnitService = organisationUnitService;
     }
 
+    @Autowired
+    private InputUtils inputUtils;
+
     // -------------------------------------------------------------------------
     // Input
     // -------------------------------------------------------------------------
@@ -107,6 +114,20 @@
         this.multiOrganisationUnit = multiOrganisationUnit;
     }
 
+    private String cc;
+
+    public void setCc( String cc )
+    {
+        this.cc = cc;
+    }
+
+    private String cp;
+
+    public void setCp( String cp )
+    {
+        this.cp = cp;
+    }
+
     private int statusCode;
 
     public int getStatusCode()
@@ -124,12 +145,13 @@
         Period period = PeriodType.getPeriodFromIsoString( periodId );
         OrganisationUnit organisationUnit = organisationUnitService.getOrganisationUnit( organisationUnitId );
         Set<OrganisationUnit> children = organisationUnit.getChildren();
+        DataElementCategoryOptionCombo attributeOptionCombo = inputUtils.getAttributeOptionCombo( ServletActionContext.getResponse(), cc, cp );
 
         // ---------------------------------------------------------------------
         // Check locked status
         // ---------------------------------------------------------------------
 
-        if ( dataSetService.isLocked( dataSet, period, organisationUnit, null, multiOrganisationUnit ) )
+        if ( dataSetService.isLocked( dataSet, period, organisationUnit, attributeOptionCombo, null, multiOrganisationUnit ) )
         {
             return logError( "Entry locked: " + dataSet + ", " + period + ", " + organisationUnit, 2 );
         }

=== modified file 'dhis-2/dhis-web/dhis-web-dataentry/src/main/resources/META-INF/dhis/beans.xml'
--- dhis-2/dhis-web/dhis-web-dataentry/src/main/resources/META-INF/dhis/beans.xml	2013-12-25 15:01:48 +0000
+++ dhis-2/dhis-web/dhis-web-dataentry/src/main/resources/META-INF/dhis/beans.xml	2014-01-02 13:36:45 +0000
@@ -26,7 +26,6 @@
     <property name="dataSetService" ref="org.hisp.dhis.dataset.DataSetService" />
     <property name="registrationService" ref="org.hisp.dhis.dataset.CompleteDataSetRegistrationService" />
     <property name="organisationUnitService" ref="org.hisp.dhis.organisationunit.OrganisationUnitService" />
-    <property name="categoryService" ref="org.hisp.dhis.dataelement.DataElementCategoryService" />
   </bean>
 
   <bean id="org.hisp.dhis.de.action.LoadFormAction" class="org.hisp.dhis.de.action.LoadFormAction" scope="prototype">

=== modified file 'dhis-2/dhis-web/dhis-web-dataentry/src/main/webapp/dhis-web-dataentry/javascript/form.js'
--- dhis-2/dhis-web/dhis-web-dataentry/src/main/webapp/dhis-web-dataentry/javascript/form.js	2013-12-25 15:01:48 +0000
+++ dhis-2/dhis-web/dhis-web-dataentry/src/main/webapp/dhis-web-dataentry/javascript/form.js	2014-01-02 13:36:45 +0000
@@ -1571,18 +1571,25 @@
 
 function registerCompleteDataSet()
 {
-	var confirmed = confirm( i18n_confirm_complete );
-	
-	if ( !confirmed )
+	if ( !confirm( i18n_confirm_complete ) )
 	{
 		return false;
 	}
 	
 	validate( true, function() {	
 	    var params = dhis2.de.storageManager.getCurrentCompleteDataSetParams();
-        params['organisationUnitId'] = getCurrentOrganisationUnit();
-        params['multiOrganisationUnit'] = dhis2.de.multiOrganisationUnit;
+        params.organisationUnitId = getCurrentOrganisationUnit();
+        params.multiOrganisationUnit = dhis2.de.multiOrganisationUnit;
 
+        var cc = dhis2.de.getCurrentCategoryCombo();
+        var cp = dhis2.de.getCurrentCategoryOptionsQueryValue();
+        
+        if ( cc && cp )
+        {
+        	params.cc = cc;
+        	params.cp = cp;
+        }
+        
         dhis2.de.storageManager.saveCompleteDataSet( params );
 	
 	    $.ajax( {
@@ -1613,37 +1620,47 @@
 
 function undoCompleteDataSet()
 {
-    var confirmed = confirm( i18n_confirm_undo );
+	if ( !confirm( i18n_confirm_undo ) )
+	{
+		return false;
+	}
+	
     var params = dhis2.de.storageManager.getCurrentCompleteDataSetParams();
-    params[ 'organisationUnitId' ] = getCurrentOrganisationUnit();
-    params[ 'multiOrganisationUnit' ] = dhis2.de.multiOrganisationUnit;
+    params.organisationUnitId = getCurrentOrganisationUnit();
+    params.multiOrganisationUnit = dhis2.de.multiOrganisationUnit;
 
-    if ( confirmed )
+    var cc = dhis2.de.getCurrentCategoryCombo();
+    var cp = dhis2.de.getCurrentCategoryOptionsQueryValue();
+    
+    if ( cc && cp )
     {
-        $.ajax( {
-        	url: 'undoCompleteDataSet.action',
-        	data: params,
-        	dataType: 'json',
-        	success: function(data)
-	        {
-                if ( data.status == 2 )
-                {
-                    log( 'Data set is locked' );
-                    setHeaderMessage( i18n_unregister_complete_failed_dataset_is_locked );
-                }
-                else
-                {
-                    disableUndoButton();
-                    dhis2.de.storageManager.clearCompleteDataSet( params );
-                }
-
-	        },
-	        error: function()
-	        {
-	        	dhis2.de.storageManager.clearCompleteDataSet( params );
-	        }
-        } );
+    	params.cc = cc;
+    	params.cp = cp;
     }
+    
+    $.ajax( {
+    	url: 'undoCompleteDataSet.action',
+    	data: params,
+    	dataType: 'json',
+    	success: function(data)
+        {
+            if ( data.status == 2 )
+            {
+                log( 'Data set is locked' );
+                setHeaderMessage( i18n_unregister_complete_failed_dataset_is_locked );
+            }
+            else
+            {
+                disableUndoButton();
+                dhis2.de.storageManager.clearCompleteDataSet( params );
+            }
+
+        },
+        error: function()
+        {
+        	dhis2.de.storageManager.clearCompleteDataSet( params );
+        }
+    } );
 }
 
 function disableUndoButton()

=== modified file 'dhis-2/dhis-web/dhis-web-light/src/main/java/org/hisp/dhis/light/dataentry/action/GetPeriodsAction.java'
--- dhis-2/dhis-web/dhis-web-light/src/main/java/org/hisp/dhis/light/dataentry/action/GetPeriodsAction.java	2013-08-23 16:05:01 +0000
+++ dhis-2/dhis-web/dhis-web-light/src/main/java/org/hisp/dhis/light/dataentry/action/GetPeriodsAction.java	2014-01-02 13:36:45 +0000
@@ -222,7 +222,7 @@
     {
         for ( Period period : periods )
         {
-            if ( dataSetService.isLocked( dataSet, period, organisationUnit, null ) )
+            if ( dataSetService.isLocked( dataSet, period, organisationUnit, null, null ) ) //TODO attributes
             {
                 lockedPeriods.add( period );
             }