mirror of
https://github.com/Alfresco/alfresco-community-repo.git
synced 2025-08-14 17:58:59 +00:00
Merged HEAD (5.2) to 5.2.N (5.2.1)
126423 jkaabimofrad: Merged FILE-FOLDER-API (5.2.0) to HEAD (5.2) 121833 jvonka: FileFolder (Node) API - tweak validation error messages - also extra checks to prevent manipulation of cm:systemfolder (create/update/specialise) RA-741, RA-672, RA-753 git-svn-id: https://svn.alfresco.com/repos/alfresco-enterprise/alfresco/BRANCHES/DEV/5.2.N/root@126769 c4b6b30b-aa2e-2d43-bbcb-ca4b014f7261
This commit is contained in:
@@ -322,7 +322,7 @@ public class NodesImpl implements Nodes
|
|||||||
return nodeMatches(nodeRef, expectedTypes, excludedTypes, true);
|
return nodeMatches(nodeRef, expectedTypes, excludedTypes, true);
|
||||||
}
|
}
|
||||||
|
|
||||||
public boolean nodeMatches(NodeRef nodeRef, Set<QName> expectedTypes, Set<QName> excludedTypes, boolean existsCheck)
|
private boolean nodeMatches(NodeRef nodeRef, Set<QName> expectedTypes, Set<QName> excludedTypes, boolean existsCheck)
|
||||||
{
|
{
|
||||||
if (existsCheck && (! nodeService.exists(nodeRef)))
|
if (existsCheck && (! nodeService.exists(nodeRef)))
|
||||||
{
|
{
|
||||||
@@ -508,7 +508,7 @@ public class NodesImpl implements Nodes
|
|||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
throw new InvalidArgumentException("Node is not a folder");
|
throw new InvalidArgumentException("Node is not a folder: "+nodeRef.getId());
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -539,7 +539,7 @@ public class NodesImpl implements Nodes
|
|||||||
NodeRef person = repositoryHelper.getPerson();
|
NodeRef person = repositoryHelper.getPerson();
|
||||||
if (person == null)
|
if (person == null)
|
||||||
{
|
{
|
||||||
throw new InvalidArgumentException("Unexpected: cannot use " + PATH_MY);
|
throw new InvalidArgumentException("Unexpected - cannot use: " + PATH_MY);
|
||||||
}
|
}
|
||||||
parentNodeRef = repositoryHelper.getUserHome(person);
|
parentNodeRef = repositoryHelper.getUserHome(person);
|
||||||
if (parentNodeRef == null)
|
if (parentNodeRef == null)
|
||||||
@@ -557,7 +557,7 @@ public class NodesImpl implements Nodes
|
|||||||
// check that parent is a folder before resolving relative path
|
// check that parent is a folder before resolving relative path
|
||||||
if (! nodeMatches(parentNodeRef, Collections.singleton(ContentModel.TYPE_FOLDER), null, false))
|
if (! nodeMatches(parentNodeRef, Collections.singleton(ContentModel.TYPE_FOLDER), null, false))
|
||||||
{
|
{
|
||||||
throw new InvalidArgumentException("NodeId of folder is expected");
|
throw new InvalidArgumentException("NodeId of folder is expected: "+parentNodeRef.getId());
|
||||||
}
|
}
|
||||||
|
|
||||||
// resolve path relative to current nodeId
|
// resolve path relative to current nodeId
|
||||||
@@ -621,7 +621,7 @@ public class NodesImpl implements Nodes
|
|||||||
catch (FileNotFoundException fnfe)
|
catch (FileNotFoundException fnfe)
|
||||||
{
|
{
|
||||||
// convert checked exception
|
// convert checked exception
|
||||||
throw new EntityNotFoundException(fnfe.getMessage()+" ["+parentNodeRef+","+path+"]");
|
throw new EntityNotFoundException(fnfe.getMessage()+" ["+parentNodeRef.getId()+","+path+"]");
|
||||||
}
|
}
|
||||||
|
|
||||||
return fileInfo.getNodeRef();
|
return fileInfo.getNodeRef();
|
||||||
@@ -685,7 +685,7 @@ public class NodesImpl implements Nodes
|
|||||||
}
|
}
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
throw new RuntimeException("Unexpected - should not reach here");
|
throw new RuntimeException("Unexpected - should not reach here: "+type);
|
||||||
}
|
}
|
||||||
|
|
||||||
if (selectParam.size() > 0)
|
if (selectParam.size() > 0)
|
||||||
@@ -899,7 +899,7 @@ public class NodesImpl implements Nodes
|
|||||||
// check that resolved node is a folder
|
// check that resolved node is a folder
|
||||||
if (! nodeMatches(parentNodeRef, Collections.singleton(ContentModel.TYPE_FOLDER), null, false))
|
if (! nodeMatches(parentNodeRef, Collections.singleton(ContentModel.TYPE_FOLDER), null, false))
|
||||||
{
|
{
|
||||||
throw new InvalidArgumentException("NodeId of folder is expected");
|
throw new InvalidArgumentException("NodeId of folder is expected: "+parentNodeRef.getId());
|
||||||
}
|
}
|
||||||
|
|
||||||
final List<String> selectParam = parameters.getSelectedProperties();
|
final List<String> selectParam = parameters.getSelectedProperties();
|
||||||
@@ -1079,21 +1079,21 @@ public class NodesImpl implements Nodes
|
|||||||
|
|
||||||
if (! nodeMatches(parentNodeRef, Collections.singleton(ContentModel.TYPE_FOLDER), null, false))
|
if (! nodeMatches(parentNodeRef, Collections.singleton(ContentModel.TYPE_FOLDER), null, false))
|
||||||
{
|
{
|
||||||
throw new InvalidArgumentException("NodeId of folder is expected: "+parentNodeRef);
|
throw new InvalidArgumentException("NodeId of folder is expected: "+parentNodeRef.getId());
|
||||||
}
|
}
|
||||||
|
|
||||||
// node name - mandatory
|
// node name - mandatory
|
||||||
String nodeName = nodeInfo.getName();
|
String nodeName = nodeInfo.getName();
|
||||||
if ((nodeName == null) || nodeName.isEmpty())
|
if ((nodeName == null) || nodeName.isEmpty())
|
||||||
{
|
{
|
||||||
throw new InvalidArgumentException("Node name is expected: "+parentNodeRef);
|
throw new InvalidArgumentException("Node name is expected: "+parentNodeRef.getId());
|
||||||
}
|
}
|
||||||
|
|
||||||
// node type - check that requested type is a (sub-) type of cm:object
|
// node type - check that requested type is a (sub-) type of cm:object
|
||||||
String nodeType = nodeInfo.getNodeType();
|
String nodeType = nodeInfo.getNodeType();
|
||||||
if ((nodeType == null) || nodeType.isEmpty())
|
if ((nodeType == null) || nodeType.isEmpty())
|
||||||
{
|
{
|
||||||
throw new InvalidArgumentException("Node type is expected: "+parentNodeRef+","+nodeName);
|
throw new InvalidArgumentException("Node type is expected: "+parentNodeRef.getId()+","+nodeName);
|
||||||
}
|
}
|
||||||
|
|
||||||
QName nodeTypeQName = createQName(nodeType);
|
QName nodeTypeQName = createQName(nodeType);
|
||||||
@@ -1101,10 +1101,7 @@ public class NodesImpl implements Nodes
|
|||||||
boolean isContent = isSubClass(nodeTypeQName, ContentModel.TYPE_CONTENT);
|
boolean isContent = isSubClass(nodeTypeQName, ContentModel.TYPE_CONTENT);
|
||||||
if (! isContent)
|
if (! isContent)
|
||||||
{
|
{
|
||||||
if (! isSubClass(nodeTypeQName, ContentModel.TYPE_CMOBJECT))
|
validateCmObject(nodeTypeQName);
|
||||||
{
|
|
||||||
throw new InvalidArgumentException("Invalid type: " + nodeTypeQName + " [expected (sub-)type of cm:object]");
|
|
||||||
}
|
|
||||||
}
|
}
|
||||||
|
|
||||||
Map<QName, Serializable> props = new HashMap<>(1);
|
Map<QName, Serializable> props = new HashMap<>(1);
|
||||||
@@ -1177,16 +1174,27 @@ public class NodesImpl implements Nodes
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
|
// check cm:cmobject (but *not* cm:systemfolder)
|
||||||
|
private void validateCmObject(QName nodeTypeQName)
|
||||||
|
{
|
||||||
|
if (! isSubClass(nodeTypeQName, ContentModel.TYPE_CMOBJECT))
|
||||||
|
{
|
||||||
|
throw new InvalidArgumentException("Invalid type: " + nodeTypeQName + " - expected (sub-)type of cm:cmobject");
|
||||||
|
}
|
||||||
|
|
||||||
|
if (isSubClass(nodeTypeQName, ContentModel.TYPE_SYSTEM_FOLDER))
|
||||||
|
{
|
||||||
|
throw new InvalidArgumentException("Invalid type: " + nodeTypeQName + " - cannot be (sub-)type of cm:systemfolder");
|
||||||
|
}
|
||||||
|
}
|
||||||
|
|
||||||
public Node updateNode(String nodeId, Node nodeInfo, Parameters parameters)
|
public Node updateNode(String nodeId, Node nodeInfo, Parameters parameters)
|
||||||
{
|
{
|
||||||
final NodeRef nodeRef = validateNode(nodeId);
|
final NodeRef nodeRef = validateNode(nodeId);
|
||||||
|
|
||||||
QName nodeTypeQName = getNodeType(nodeRef);
|
QName nodeTypeQName = getNodeType(nodeRef);
|
||||||
|
|
||||||
if (! isSubClass(nodeTypeQName, ContentModel.TYPE_CMOBJECT))
|
validateCmObject(nodeTypeQName);
|
||||||
{
|
|
||||||
throw new InvalidArgumentException("Invalid type: " + nodeTypeQName + " [expected (sub-)type of cm:object]");
|
|
||||||
}
|
|
||||||
|
|
||||||
Map<QName, Serializable> props = new HashMap<>(0);
|
Map<QName, Serializable> props = new HashMap<>(0);
|
||||||
|
|
||||||
@@ -1208,7 +1216,9 @@ public class NodesImpl implements Nodes
|
|||||||
// update node type - ensure that we are performing a specialise (we do not support generalise)
|
// update node type - ensure that we are performing a specialise (we do not support generalise)
|
||||||
QName destNodeTypeQName = createQName(nodeType);
|
QName destNodeTypeQName = createQName(nodeType);
|
||||||
|
|
||||||
if ((! destNodeTypeQName.equals(nodeTypeQName)) && isSubClass(destNodeTypeQName, nodeTypeQName))
|
if ((! destNodeTypeQName.equals(nodeTypeQName)) &&
|
||||||
|
isSubClass(destNodeTypeQName, nodeTypeQName) &&
|
||||||
|
(! isSubClass(destNodeTypeQName, ContentModel.TYPE_SYSTEM_FOLDER)))
|
||||||
{
|
{
|
||||||
nodeService.setType(nodeRef, destNodeTypeQName);
|
nodeService.setType(nodeRef, destNodeTypeQName);
|
||||||
}
|
}
|
||||||
@@ -1354,25 +1364,25 @@ public class NodesImpl implements Nodes
|
|||||||
}
|
}
|
||||||
catch (InvalidNodeRefException inre)
|
catch (InvalidNodeRefException inre)
|
||||||
{
|
{
|
||||||
throw new EntityNotFoundException(inre.getMessage()+" ["+nodeRef+","+parentNodeRef+"]");
|
throw new EntityNotFoundException(inre.getMessage());
|
||||||
}
|
}
|
||||||
catch (FileNotFoundException fnfe)
|
catch (FileNotFoundException fnfe)
|
||||||
{
|
{
|
||||||
// convert checked exception
|
// convert checked exception
|
||||||
throw new EntityNotFoundException(fnfe.getMessage()+" ["+nodeRef+","+parentNodeRef+"]");
|
throw new EntityNotFoundException(fnfe.getMessage());
|
||||||
}
|
}
|
||||||
catch (FileExistsException fee)
|
catch (FileExistsException fee)
|
||||||
{
|
{
|
||||||
// duplicate - name clash
|
// duplicate - name clash
|
||||||
throw new ConstraintViolatedException(fee.getMessage()+" ["+nodeRef+","+parentNodeRef+"]");
|
throw new ConstraintViolatedException(fee.getMessage());
|
||||||
}
|
}
|
||||||
catch (FileFolderServiceImpl.InvalidTypeException ite)
|
catch (FileFolderServiceImpl.InvalidTypeException ite)
|
||||||
{
|
{
|
||||||
throw new InvalidArgumentException(ite.getMessage()+" ["+nodeRef+","+parentNodeRef+"]");
|
throw new InvalidArgumentException(ite.getMessage());
|
||||||
}
|
}
|
||||||
catch (CyclicChildRelationshipException ccre)
|
catch (CyclicChildRelationshipException ccre)
|
||||||
{
|
{
|
||||||
throw new InvalidArgumentException(ccre.getMessage() + " [" + nodeRef + "," + parentNodeRef + "]");
|
throw new InvalidArgumentException(ccre.getMessage());
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
@@ -1383,7 +1393,7 @@ public class NodesImpl implements Nodes
|
|||||||
|
|
||||||
if (! nodeMatches(nodeRef, Collections.singleton(ContentModel.TYPE_CONTENT), null, false))
|
if (! nodeMatches(nodeRef, Collections.singleton(ContentModel.TYPE_CONTENT), null, false))
|
||||||
{
|
{
|
||||||
throw new InvalidArgumentException("NodeId of content is expected: "+nodeRef);
|
throw new InvalidArgumentException("NodeId of content is expected: "+nodeRef.getId());
|
||||||
}
|
}
|
||||||
|
|
||||||
Map<QName, Serializable> nodeProps = nodeService.getProperties(nodeRef);
|
Map<QName, Serializable> nodeProps = nodeService.getProperties(nodeRef);
|
||||||
@@ -1426,9 +1436,9 @@ public class NodesImpl implements Nodes
|
|||||||
{
|
{
|
||||||
final NodeRef nodeRef = validateNode(fileNodeId);
|
final NodeRef nodeRef = validateNode(fileNodeId);
|
||||||
|
|
||||||
if (!nodeMatches(nodeRef, Collections.singleton(ContentModel.TYPE_CONTENT), null, false))
|
if (! nodeMatches(nodeRef, Collections.singleton(ContentModel.TYPE_CONTENT), null, false))
|
||||||
{
|
{
|
||||||
throw new InvalidArgumentException("NodeId of content is expected: " + nodeRef);
|
throw new InvalidArgumentException("NodeId of content is expected: " + nodeRef.getId());
|
||||||
}
|
}
|
||||||
|
|
||||||
ContentWriter writer = contentService.getWriter(nodeRef, ContentModel.PROP_CONTENT, true);
|
ContentWriter writer = contentService.getWriter(nodeRef, ContentModel.PROP_CONTENT, true);
|
||||||
@@ -1473,13 +1483,14 @@ public class NodesImpl implements Nodes
|
|||||||
{
|
{
|
||||||
if (formData == null || !formData.getIsMultiPart())
|
if (formData == null || !formData.getIsMultiPart())
|
||||||
{
|
{
|
||||||
throw new InvalidArgumentException("The request content-type is not multipart");
|
throw new InvalidArgumentException("The request content-type is not multipart: "+parentFolderNodeId);
|
||||||
}
|
}
|
||||||
|
|
||||||
final NodeRef parentNodeRef = validateOrLookupNode(parentFolderNodeId, null);
|
final NodeRef parentNodeRef = validateOrLookupNode(parentFolderNodeId, null);
|
||||||
if (Type.DOCUMENT == getType(parentNodeRef))
|
|
||||||
|
if (! nodeMatches(parentNodeRef, Collections.singleton(ContentModel.TYPE_FOLDER), null, false))
|
||||||
{
|
{
|
||||||
throw new InvalidArgumentException(parentFolderNodeId + " is not a folder.");
|
throw new InvalidArgumentException("NodeId of folder is expected: "+parentNodeRef.getId());
|
||||||
}
|
}
|
||||||
|
|
||||||
String fileName = null;
|
String fileName = null;
|
||||||
@@ -1537,7 +1548,7 @@ public class NodesImpl implements Nodes
|
|||||||
// result in a success message, but the files do not appear.
|
// result in a success message, but the files do not appear.
|
||||||
if (formData.getFields().length == 0)
|
if (formData.getFields().length == 0)
|
||||||
{
|
{
|
||||||
throw new ConstraintViolatedException(" No disk space available");
|
throw new ConstraintViolatedException("No disk space available");
|
||||||
}
|
}
|
||||||
// Ensure mandatory file attributes have been located. Need either
|
// Ensure mandatory file attributes have been located. Need either
|
||||||
// destination, or site + container or updateNodeRef
|
// destination, or site + container or updateNodeRef
|
||||||
|
Reference in New Issue
Block a user