diff --git a/rm-server/config/alfresco/module/org_alfresco_module_rm/classified-content-context.xml b/rm-server/config/alfresco/module/org_alfresco_module_rm/classified-content-context.xml
index ad6f3419a3..5c8d015a25 100644
--- a/rm-server/config/alfresco/module/org_alfresco_module_rm/classified-content-context.xml
+++ b/rm-server/config/alfresco/module/org_alfresco_module_rm/classified-content-context.xml
@@ -195,6 +195,7 @@
parent="baseService" init-method="init">
+
diff --git a/rm-server/source/java/org/alfresco/module/org_alfresco_module_rm/classification/ContentClassificationServiceImpl.java b/rm-server/source/java/org/alfresco/module/org_alfresco_module_rm/classification/ContentClassificationServiceImpl.java
index a50e923900..a25fe1ae1e 100644
--- a/rm-server/source/java/org/alfresco/module/org_alfresco_module_rm/classification/ContentClassificationServiceImpl.java
+++ b/rm-server/source/java/org/alfresco/module/org_alfresco_module_rm/classification/ContentClassificationServiceImpl.java
@@ -34,9 +34,11 @@ import org.alfresco.module.org_alfresco_module_rm.classification.ClassificationE
import org.alfresco.module.org_alfresco_module_rm.classification.ClassificationException.LevelIdNotFound;
import org.alfresco.module.org_alfresco_module_rm.classification.ClassificationException.ReasonIdNotFound;
import org.alfresco.module.org_alfresco_module_rm.classification.model.ClassifiedContentModel;
+import org.alfresco.module.org_alfresco_module_rm.freeze.FreezeService;
import org.alfresco.module.org_alfresco_module_rm.util.ServiceBaseImpl;
import org.alfresco.repo.security.authentication.AuthenticationUtil;
import org.alfresco.repo.security.authentication.AuthenticationUtil.RunAsWork;
+import org.alfresco.repo.security.permissions.AccessDeniedException;
import org.alfresco.service.cmr.repository.InvalidNodeRefException;
import org.alfresco.service.cmr.repository.NodeRef;
import org.alfresco.service.namespace.QName;
@@ -54,11 +56,13 @@ public class ContentClassificationServiceImpl extends ServiceBaseImpl
private ClassificationReasonManager reasonManager;
private SecurityClearanceService securityClearanceService;
private ClassificationServiceBootstrap classificationServiceBootstrap;
+ private FreezeService freezeService;
public void setLevelManager(ClassificationLevelManager levelManager) { this.levelManager = levelManager; }
public void setReasonManager(ClassificationReasonManager reasonManager) { this.reasonManager = reasonManager; }
public void setSecurityClearanceService(SecurityClearanceService securityClearanceService) { this.securityClearanceService = securityClearanceService; }
public void setClassificationServiceBootstrap(ClassificationServiceBootstrap classificationServiceBootstrap) { this.classificationServiceBootstrap = classificationServiceBootstrap; }
+ public void setFreezeService(FreezeService service) { this.freezeService = service; }
public void init()
{
@@ -91,7 +95,7 @@ public class ContentClassificationServiceImpl extends ServiceBaseImpl
};
/**
- * @see org.alfresco.module.org_alfresco_module_rm.classification.ContentClassificationService#classifyContent(java.lang.String, java.lang.String, java.lang.String, java.util.Set, org.alfresco.service.cmr.repository.NodeRef)
+ * @see org.alfresco.module.org_alfresco_module_rm.classification.ContentClassificationService#classifyContent(ClassificationAspectProperties, NodeRef)
*/
@Override
public void classifyContent(ClassificationAspectProperties classificationAspectProperties, final NodeRef content)
@@ -106,6 +110,11 @@ public class ContentClassificationServiceImpl extends ServiceBaseImpl
{
public Void doWork()
{
+ if (freezeService.isFrozen(content))
+ {
+ throw new AccessDeniedException("Frozen nodes can not be classified.");
+ }
+
nodeService.addAspect(content, ASPECT_CLASSIFIED, properties);
return null;
}
@@ -229,7 +238,7 @@ public class ContentClassificationServiceImpl extends ServiceBaseImpl
}
/**
- * @see org.alfresco.module.org_alfresco_module_rm.classification.ContentClassificationService#editClassifiedContent(java.lang.String, java.lang.String, java.lang.String, java.util.Set, org.alfresco.service.cmr.repository.NodeRef)
+ * @see org.alfresco.module.org_alfresco_module_rm.classification.ContentClassificationService#editClassifiedContent(ClassificationAspectProperties, NodeRef)
*/
@Override
public void editClassifiedContent(ClassificationAspectProperties classificationAspectProperties, NodeRef content)
diff --git a/rm-server/unit-test/java/org/alfresco/module/org_alfresco_module_rm/classification/ContentClassificationServiceImplUnitTest.java b/rm-server/unit-test/java/org/alfresco/module/org_alfresco_module_rm/classification/ContentClassificationServiceImplUnitTest.java
index dc91746ae2..bc141bcc5c 100644
--- a/rm-server/unit-test/java/org/alfresco/module/org_alfresco_module_rm/classification/ContentClassificationServiceImplUnitTest.java
+++ b/rm-server/unit-test/java/org/alfresco/module/org_alfresco_module_rm/classification/ContentClassificationServiceImplUnitTest.java
@@ -23,6 +23,7 @@ import static org.alfresco.module.org_alfresco_module_rm.test.util.AlfMock.gener
import static org.junit.Assert.assertEquals;
import static org.junit.Assert.assertFalse;
import static org.junit.Assert.assertTrue;
+import static org.mockito.Matchers.any;
import static org.mockito.Matchers.eq;
import static org.mockito.Mockito.mock;
import static org.mockito.Mockito.verify;
@@ -43,8 +44,10 @@ import org.alfresco.model.QuickShareModel;
import org.alfresco.module.org_alfresco_module_rm.classification.ClassificationException.InvalidNode;
import org.alfresco.module.org_alfresco_module_rm.classification.ClassificationException.LevelIdNotFound;
import org.alfresco.module.org_alfresco_module_rm.classification.model.ClassifiedContentModel;
+import org.alfresco.module.org_alfresco_module_rm.freeze.FreezeService;
import org.alfresco.module.org_alfresco_module_rm.test.util.MockAuthenticationUtilHelper;
import org.alfresco.module.org_alfresco_module_rm.util.AuthenticationUtil;
+import org.alfresco.repo.security.permissions.AccessDeniedException;
import org.alfresco.service.cmr.dictionary.DictionaryService;
import org.alfresco.service.cmr.repository.NodeRef;
import org.alfresco.service.cmr.repository.NodeService;
@@ -74,6 +77,7 @@ public class ContentClassificationServiceImplUnitTest implements ClassifiedConte
@Mock ClassificationReasonManager mockReasonManager;
@Mock NodeService mockNodeService;
@Mock DictionaryService mockDictionaryService;
+ @Mock FreezeService mockFreezeService;
@Mock SecurityClearanceService mockSecurityClearanceService;
@Mock AuthenticationUtil mockAuthenticationUtil;
@Mock ClassificationAspectProperties mockPropertiesDTO;
@@ -101,6 +105,7 @@ public class ContentClassificationServiceImplUnitTest implements ClassifiedConte
NodeRef content = new NodeRef("fake://content/");
when(mockDictionaryService.isSubClass(mockNodeService.getType(content), ContentModel.TYPE_CONTENT)).thenReturn(true);
when(mockNodeService.hasAspect(content, ClassifiedContentModel.ASPECT_CLASSIFIED)).thenReturn(false);
+ when(mockFreezeService.isFrozen(any(NodeRef.class))).thenReturn(false);
when(mockSecurityClearanceService.isCurrentUserClearedForClassification("levelId1")).thenReturn(true);
// Set up the mock DTO.
when(mockPropertiesDTO.getClassificationLevelId()).thenReturn("levelId1");
@@ -179,6 +184,33 @@ public class ContentClassificationServiceImplUnitTest implements ClassifiedConte
contentClassificationServiceImpl.validateProperties(mockPropertiesDTO);
}
+ /**
+ * Check that a user can't classify content that is frozen.
+ */
+ @Test(expected = AccessDeniedException.class)
+ public void classifyContent_frozen()
+ {
+ ClassificationLevel level = new ClassificationLevel("levelId1", "displayLabelKey");
+ ClassificationReason reason1 = new ClassificationReason("reasonId1", "displayLabelKey1");
+ // Set up the managers to return these objects when the ids are provided.
+ when(mockLevelManager.findLevelById("levelId1")).thenReturn(level);
+ when(mockReasonManager.findReasonById("reasonId1")).thenReturn(reason1);
+ // Create a content node.
+ NodeRef content = new NodeRef("fake://content/");
+ when(mockDictionaryService.isSubClass(mockNodeService.getType(content), ContentModel.TYPE_CONTENT)).thenReturn(true);
+ when(mockNodeService.hasAspect(content, ClassifiedContentModel.ASPECT_CLASSIFIED)).thenReturn(false);
+ when(mockFreezeService.isFrozen(any(NodeRef.class))).thenReturn(true);
+ when(mockSecurityClearanceService.isCurrentUserClearedForClassification("levelId1")).thenReturn(true);
+ // Set up the mock DTO.
+ when(mockPropertiesDTO.getClassificationLevelId()).thenReturn("levelId1");
+ when(mockPropertiesDTO.getClassifiedBy()).thenReturn("classifiedBy");
+ when(mockPropertiesDTO.getClassificationAgency()).thenReturn("classificationAgency");
+ when(mockPropertiesDTO.getClassificationReasonIds()).thenReturn(Sets.newHashSet("reasonId1", "reasonId2"));
+
+ // Call the method under test
+ contentClassificationServiceImpl.classifyContent(mockPropertiesDTO, content);
+ }
+
/**
* Given that a node does not have the classify aspect applied
* When I ask for the nodes classification