Skip to content

HTTPS clone URL

Subversion checkout URL

You can clone with
or
.
Download ZIP
Browse files

Merge branch 'feature/fix-inherited-perms' into develop

Conflicts:
	test/src/org/exist/security/XMLDBSecurityTest.java
  • Loading branch information...
commit da52593923470a4b19631e5f57f18f366deae018 2 parents eecd931 + a25dad0
@adamretter adamretter authored
View
2  extensions/versioning/src/org/exist/versioning/VersioningTrigger.java
@@ -292,7 +292,7 @@ private void before(DBBroker broker, Txn transaction, DocumentImpl document, boo
vDoc = vCollection.getDocument(broker, binUri);
} else {
vDoc = new DocumentImpl(broker.getBrokerPool(), vCollection, XmldbURI.createInternal(vFileName));
- vDoc.copyOf(document);
+ vDoc.copyOf(document, true);
vDoc.copyChildren(document);
}
View
4 src/org/exist/collections/Collection.java
@@ -902,7 +902,7 @@ final public Permission getPermissions() {
}
}
- final public Permission getPermissionsNoLock() {
+ public Permission getPermissionsNoLock() {
return permissions;
}
@@ -1677,7 +1677,7 @@ private IndexInfo validateXMLResourceInternal(final Txn transaction, final DBBro
} else {
//TODO : use a more elaborated method ? No triggers...
broker.removeXMLResource(transaction, oldDoc, false);
- oldDoc.copyOf(document);
+ oldDoc.copyOf(document, true);
indexer.setDocumentObject(oldDoc);
//old has become new at this point
document = oldDoc;
View
26 src/org/exist/dom/DocumentImpl.java
@@ -312,8 +312,13 @@ public DocumentMetadata getMetadata() {
* This is called by {@link Collection} when replacing a document.
*
* @param other a <code>DocumentImpl</code> value
+ * @param preserve Cause copyOf to preserve the following attributes of
+ * each source file in the copy: modification time,
+ * access time, file mode, user ID, and group ID,
+ * as allowed by permissions and Access Control
+ * Lists (ACLs)
*/
- public void copyOf(DocumentImpl other) {
+ public void copyOf(final DocumentImpl other, final boolean preserve) {
childAddress = null;
children = 0;
@@ -326,16 +331,21 @@ public void copyOf(DocumentImpl other) {
//copy metadata
metadata.copyOf(other.getMetadata());
- //update timestamp
- final long timestamp = System.currentTimeMillis();
- metadata.setCreated(timestamp);
- metadata.setLastModified(timestamp);
+ if(preserve) {
+ //copy permission
+ permissions = ((UnixStylePermission)other.permissions).copy();
+ //created and last modified are done by metadata.copyOf
+ //metadata.setCreated(other.getMetadata().getCreated());
+ //metadata.setLastModified(other.getMetadata().getLastModified());
+ } else {
+ //update timestamp
+ final long timestamp = System.currentTimeMillis();
+ metadata.setCreated(timestamp);
+ metadata.setLastModified(timestamp);
+ }
// reset pageCount: will be updated during storage
metadata.setPageCount(0);
-
- //copy permission
- permissions = ((UnixStylePermission)other.permissions).copy();
}
/**
View
82 src/org/exist/storage/NativeBroker.java
@@ -48,6 +48,7 @@
import org.exist.Indexer;
import org.exist.backup.RawDataBackup;
import org.exist.collections.Collection;
+import org.exist.collections.Collection.CollectionEntry;
import org.exist.collections.Collection.SubCollectionEntry;
import org.exist.collections.CollectionCache;
import org.exist.collections.CollectionConfiguration;
@@ -995,32 +996,34 @@ private Collection openCollection(XmldbURI uri, long addr, int lockMode) throws
/**
* Checks all permissions in the tree to ensure that a copy operation will succeed
*/
- final void checkPermissionsForCopy(final Collection src, final XmldbURI destUri) throws PermissionDeniedException, LockException {
+ protected void checkPermissionsForCopy(final Collection src, final XmldbURI destUri, final XmldbURI newName) throws PermissionDeniedException, LockException {
if(!src.getPermissionsNoLock().validate(getSubject(), Permission.EXECUTE | Permission.READ)) {
throw new PermissionDeniedException("Permission denied to copy collection " + src.getURI() + " by " + getSubject().getName());
}
-
-
+
final Collection dest = getCollection(destUri);
- final XmldbURI newDestUri = destUri.append(src.getURI().lastSegment());
+ final XmldbURI newDestUri = destUri.append(newName);
final Collection newDest = getCollection(newDestUri);
if(dest != null) {
- if(!dest.getPermissionsNoLock().validate(getSubject(), Permission.EXECUTE | Permission.WRITE | Permission.READ)) {
+ //if(!dest.getPermissionsNoLock().validate(getSubject(), Permission.EXECUTE | Permission.WRITE | Permission.READ)) {
+ //TODO do we really need WRITE permission on the dest?
+ if(!dest.getPermissionsNoLock().validate(getSubject(), Permission.EXECUTE | Permission.WRITE)) {
throw new PermissionDeniedException("Permission denied to copy collection " + src.getURI() + " to " + dest.getURI() + " by " + getSubject().getName());
}
if(newDest != null) {
- if(!dest.getPermissionsNoLock().validate(getSubject(), Permission.EXECUTE | Permission.READ)) {
+ //TODO why do we need READ access on the dest collection?
+ /*if(!dest.getPermissionsNoLock().validate(getSubject(), Permission.EXECUTE | Permission.READ)) {
throw new PermissionDeniedException("Permission denied to copy collection " + src.getURI() + " to " + dest.getURI() + " by " + getSubject().getName());
- }
+ }*/
- if(newDest.isEmpty(this)) {
- if(!dest.getPermissionsNoLock().validate(getSubject(), Permission.WRITE)) {
- throw new PermissionDeniedException("Permission denied to copy collection " + src.getURI() + " to " + dest.getURI() + " by " + getSubject().getName());
+ //if(newDest.isEmpty(this)) {
+ if(!newDest.getPermissionsNoLock().validate(getSubject(), Permission.EXECUTE | Permission.WRITE)) {
+ throw new PermissionDeniedException("Permission denied to copy collection " + src.getURI() + " to " + newDest.getURI() + " by " + getSubject().getName());
}
- }
+ //}
}
}
@@ -1029,17 +1032,14 @@ final void checkPermissionsForCopy(final Collection src, final XmldbURI destUri)
if(!srcSubDoc.getPermissions().validate(getSubject(), Permission.READ)) {
throw new PermissionDeniedException("Permission denied to copy collection " + src.getURI() + " for resource " + srcSubDoc.getURI() + " by " + getSubject().getName());
}
-
+
+ //if the destination resource exists, we must have write access to replace it's metadata etc. (this follows the Linux convention)
if(newDest != null && !newDest.isEmpty(this)) {
final DocumentImpl newDestSubDoc = newDest.getDocument(this, srcSubDoc.getFileURI()); //TODO check this uri is just the filename!
if(newDestSubDoc != null) {
if(!newDestSubDoc.getPermissions().validate(getSubject(), Permission.WRITE)) {
throw new PermissionDeniedException("Permission denied to copy collection " + src.getURI() + " for resource " + newDestSubDoc.getURI() + " by " + getSubject().getName());
}
- } else {
- if(!dest.getPermissionsNoLock().validate(getSubject(), Permission.WRITE)) {
- throw new PermissionDeniedException("Permission denied to copy collection " + src.getURI() + " to " + dest.getURI() + " by " + getSubject().getName());
- }
}
}
}
@@ -1048,7 +1048,7 @@ final void checkPermissionsForCopy(final Collection src, final XmldbURI destUri)
final XmldbURI srcSubColUri = itSrcSubColUri.next();
final Collection srcSubCol = getCollection(src.getURI().append(srcSubColUri));
- checkPermissionsForCopy(srcSubCol, newDestUri);
+ checkPermissionsForCopy(srcSubCol, newDestUri, srcSubColUri);
}
}
@@ -1092,7 +1092,7 @@ public void copyCollection(final Txn transaction, final Collection collection, f
triggersVisitor.beforeCopyCollection(this, transaction, collection, dstURI);
//atomically check all permissions in the tree to ensure a copy operation will succeed before starting copying
- checkPermissionsForCopy(collection, destination.getURI());
+ checkPermissionsForCopy(collection, destination.getURI(), newName);
final Collection newCollection = doCopyCollection(transaction, collection, destination, newName);
@@ -1106,29 +1106,47 @@ public void copyCollection(final Txn transaction, final Collection collection, f
private Collection doCopyCollection(final Txn transaction, final Collection collection, final Collection destination, XmldbURI newName) throws PermissionDeniedException, IOException, EXistException, TriggerException, LockException {
- if(newName == null)
- {newName = collection.getURI().lastSegment();}
-
+ if(newName == null) {
+ newName = collection.getURI().lastSegment();
+ }
newName = destination.getURI().append(newName);
- if (LOG.isDebugEnabled())
- {LOG.debug("Copying collection to '" + newName + "'");}
+ if(LOG.isDebugEnabled()) {
+ LOG.debug("Copying collection to '" + newName + "'");
+ }
final Collection destCollection = getOrCreateCollection(transaction, newName);
for(final Iterator<DocumentImpl> i = collection.iterator(this); i.hasNext(); ) {
final DocumentImpl child = i.next();
- if (LOG.isDebugEnabled())
- {LOG.debug("Copying resource: '" + child.getURI() + "'");}
+ if(LOG.isDebugEnabled()) {
+ LOG.debug("Copying resource: '" + child.getURI() + "'");
+ }
+
+ //TODO The code below seems quite different to that in NativeBroker#copyResource presumably should be the same?
+
final XmldbURI newUri = destCollection.getURI().append(child.getFileURI());
pool.getDocumentTrigger().beforeCopyDocument(this, transaction, child, newUri);
+ //are we overwriting an existing document?
+ final CollectionEntry oldDoc;
+ if(destCollection.hasDocument(this, child.getFileURI())) {
+ oldDoc = destCollection.getResourceEntry(this, child.getFileURI().toString());
+ } else {
+ oldDoc = null;
+ }
+
DocumentImpl createdDoc;
if (child.getResourceType() == DocumentImpl.XML_FILE) {
//TODO : put a lock on newDoc ?
final DocumentImpl newDoc = new DocumentImpl(pool, destCollection, child.getFileURI());
- newDoc.copyOf(child);
+ newDoc.copyOf(child, false);
+ if(oldDoc != null) {
+ //preserve permissions from existing doc we are replacing
+ newDoc.setPermissions(oldDoc.getPermissions()); //TODO use newDoc.copyOf(oldDoc) ideally, but we cannot currently access oldDoc without READ access to it, which we may not have (and should not need for this)!
+ }
+
newDoc.setDocId(getNextResourceId(transaction, destination));
copyXMLResource(transaction, child, newDoc);
storeXMLResource(transaction, newDoc);
@@ -1137,7 +1155,11 @@ private Collection doCopyCollection(final Txn transaction, final Collection coll
createdDoc = newDoc;
} else {
final BinaryDocument newDoc = new BinaryDocument(pool, destCollection, child.getFileURI());
- newDoc.copyOf(child);
+ newDoc.copyOf(child, false);
+ if(oldDoc != null) {
+ //preserve permissions from existing doc we are replacing
+ newDoc.setPermissions(oldDoc.getPermissions()); //TODO use newDoc.copyOf(oldDoc) ideally, but we cannot currently access oldDoc without READ access to it, which we may not have (and should not need for this)!
+ }
newDoc.setDocId(getNextResourceId(transaction, destination));
InputStream is = null;
@@ -2499,6 +2521,7 @@ public void copyResource(Txn transaction, DocumentImpl doc, Collection destinati
throw new PermissionDeniedException("A resource with the same name already exists in the target collection '" + oldDoc.getURI() + "', and you do not have write access on that resource.");
}
+ //TODO these should not be here?!?
getDatabase().getDocumentTrigger().beforeDeleteDocument(this, transaction, oldDoc);
getDatabase().getDocumentTrigger().afterDeleteDocument(this, transaction, newURI);
}
@@ -2520,9 +2543,8 @@ public void copyResource(Txn transaction, DocumentImpl doc, Collection destinati
}
} else {
DocumentImpl newDoc = new DocumentImpl(pool, destination, newName);
- newDoc.copyOf(doc);
+ newDoc.copyOf(doc, oldDoc != null);
newDoc.setDocId(getNextResourceId(transaction, destination));
- //newDoc.setPermissions(doc.getPermissions());
newDoc.getUpdateLock().acquire(Lock.WRITE_LOCK);
try {
copyXMLResource(transaction, doc, newDoc);
@@ -3017,7 +3039,7 @@ public Object start() {
}.run();
// create a copy of the old doc to copy the nodes into it
final DocumentImpl tempDoc = new DocumentImpl(pool, doc.getCollection(), doc.getFileURI());
- tempDoc.copyOf(doc);
+ tempDoc.copyOf(doc, true);
tempDoc.setDocId(doc.getDocId());
indexController.setDocument(doc, StreamListener.STORE);
final StreamListener listener = indexController.getStreamListener();
View
21 src/org/exist/xmldb/LocalCollectionManagementService.java
@@ -465,10 +465,11 @@ public void copyResource(XmldbURI resourcePath, XmldbURI destinationPath, XmldbU
throws XMLDBException {
resourcePath = parent.getPathURI().resolveCollectionPath(resourcePath);
- if (destinationPath == null)
- {destinationPath = resourcePath.removeLastSegment();}
- else
- {destinationPath = parent.getPathURI().resolveCollectionPath(destinationPath);}
+ if(destinationPath == null) {
+ destinationPath = resourcePath.removeLastSegment();
+ } else {
+ destinationPath = parent.getPathURI().resolveCollectionPath(destinationPath);
+ }
final Subject preserveSubject = brokerPool.getSubject();
final TransactionManager transact = brokerPool.getTransactionManager();
@@ -493,9 +494,9 @@ public void copyResource(XmldbURI resourcePath, XmldbURI destinationPath, XmldbU
transact.abort(transaction);
throw new XMLDBException(ErrorCodes.NO_SUCH_COLLECTION, "Collection " + destinationPath + " not found");
}
- if (newName == null) {
- newName = resourcePath.lastSegment();
- }
+ if(newName == null) {
+ newName = resourcePath.lastSegment();
+ }
broker.copyResource(transaction, doc, destination, newName);
transact.commit(transaction);
} catch ( final EXistException e ) {
@@ -520,12 +521,12 @@ public void copyResource(XmldbURI resourcePath, XmldbURI destinationPath, XmldbU
}
}
- public void setCollection( Collection parent ) throws XMLDBException {
+ public void setCollection(Collection parent) throws XMLDBException {
this.parent = (LocalCollection) parent;
}
- public void setProperty( String property,
- String value ) {
+ public void setProperty(String property,
+ String value) {
}
@Override
View
88 src/org/exist/xmldb/LocalUserManagementService.java
@@ -336,6 +336,52 @@ public Void modify(DocumentImpl document) throws SyntaxException, PermissionDeni
}
@Override
+ public void chgrp(final String group) throws XMLDBException {
+ final XmldbURI collUri = collection.getPathURI();
+
+ try {
+ executeWithBroker(new BrokerOperation<Void>() {
+ @Override
+ public Void withBroker(final DBBroker broker) throws XMLDBException, LockException, PermissionDeniedException, IOException, EXistException, TriggerException, SyntaxException {
+ return modifyCollection(broker, collUri, new DatabaseItemModifier<org.exist.collections.Collection, Void>() {
+ @Override
+ public Void modify(org.exist.collections.Collection collection) throws PermissionDeniedException, SyntaxException, LockException {
+ final Permission permission = collection.getPermissionsNoLock();
+ permission.setGroup(group);
+ return null;
+ }
+ });
+ }
+ });
+ } catch(final Exception e) {
+ throw new XMLDBException(ErrorCodes.VENDOR_ERROR, "Failed to modify permission on Collection '" + collUri.toString() + "'", e);
+ }
+ }
+
+ @Override
+ public void chown(final Account u) throws XMLDBException {
+ final XmldbURI collUri = collection.getPathURI();
+
+ try {
+ executeWithBroker(new BrokerOperation<Void>() {
+ @Override
+ public Void withBroker(final DBBroker broker) throws XMLDBException, LockException, PermissionDeniedException, IOException, EXistException, TriggerException, SyntaxException {
+ return modifyCollection(broker, collUri, new DatabaseItemModifier<org.exist.collections.Collection, Void>() {
+ @Override
+ public Void modify(org.exist.collections.Collection collection) throws PermissionDeniedException, SyntaxException, LockException {
+ final Permission permission = collection.getPermissionsNoLock();
+ permission.setOwner(u);
+ return null;
+ }
+ });
+ }
+ });
+ } catch(final Exception e) {
+ throw new XMLDBException(ErrorCodes.VENDOR_ERROR, "Failed to modify permission on Collection '" + collUri.toString() + "'", e);
+ }
+ }
+
+ @Override
public void chown(final Account u, final String group) throws XMLDBException {
final XmldbURI collUri = collection.getPathURI();
@@ -360,6 +406,48 @@ public Void modify(org.exist.collections.Collection collection) throws Permissio
}
@Override
+ public void chgrp(final Resource resource, final String group) throws XMLDBException {
+ try {
+ executeWithBroker(new BrokerOperation() {
+ @Override
+ public Void withBroker(final DBBroker broker) throws XMLDBException, LockException, PermissionDeniedException, IOException, EXistException, TriggerException, SyntaxException {
+ return modifyResource(broker, resource, new DatabaseItemModifier<DocumentImpl, Void>() {
+ @Override
+ public Void modify(DocumentImpl document) throws PermissionDeniedException, LockException {
+ document.getPermissions().setGroup(group);
+ return null;
+ }
+ });
+ }
+ });
+ } catch(final Exception e) {
+ throw new XMLDBException(ErrorCodes.VENDOR_ERROR, "Failed to modify permission on Resource '" + resource.getId() + "'", e);
+ }
+
+ }
+
+ @Override
+ public void chown(final Resource resource, final Account u) throws XMLDBException {
+ try {
+ executeWithBroker(new BrokerOperation() {
+ @Override
+ public Void withBroker(final DBBroker broker) throws XMLDBException, LockException, PermissionDeniedException, IOException, EXistException, TriggerException, SyntaxException {
+ return modifyResource(broker, resource, new DatabaseItemModifier<DocumentImpl, Void>() {
+ @Override
+ public Void modify(DocumentImpl document) throws PermissionDeniedException, LockException {
+ document.getPermissions().setOwner(u);
+ return null;
+ }
+ });
+ }
+ });
+ } catch(final Exception e) {
+ throw new XMLDBException(ErrorCodes.VENDOR_ERROR, "Failed to modify permission on Resource '" + resource.getId() + "'", e);
+ }
+
+ }
+
+ @Override
public void chown(final Resource resource, final Account u, final String group) throws XMLDBException {
try {
executeWithBroker(new BrokerOperation() {
View
139 src/org/exist/xmldb/RemoteUserManagementService.java
@@ -311,13 +311,51 @@ public void unlockResource(Resource res) throws XMLDBException {
throw new XMLDBException(ErrorCodes.VENDOR_ERROR, e.getMessage(), e);
}
}
-
+
+ /**
+ * Change the owner gid of the current collection
+ *
+ * @param group Description of the Parameter
+ * @exception XMLDBException Description of the Exception
+ */
+ @Override
+ public void chgrp(String group) throws XMLDBException {
+ try {
+ final List<Object> params = new ArrayList<Object>(4);
+ params.add(parent.getPath());
+ params.add(group);
+
+ parent.getClient().execute("chgrp", params);
+ } catch (final XmlRpcException e) {
+ throw new XMLDBException(ErrorCodes.VENDOR_ERROR, e.getMessage(), e);
+ }
+ }
+
+ /**
+ * Change the owner uid of the current collection
+ *
+ * @param u Description of the Parameter
+ * @exception XMLDBException Description of the Exception
+ */
+ @Override
+ public void chown(Account u) throws XMLDBException {
+ try {
+ final List<Object> params = new ArrayList<Object>(4);
+ params.add(parent.getPath());
+ params.add(u.getName());
+
+ parent.getClient().execute("chown", params);
+ } catch (final XmlRpcException e) {
+ throw new XMLDBException(ErrorCodes.VENDOR_ERROR, e.getMessage(), e);
+ }
+ }
+
/**
- * Change the owner of the current collection
+ * Change the owner of the current collection
*
- *@param u Description of the Parameter
- *@param group Description of the Parameter
- *@exception XMLDBException Description of the Exception
+ * @param u Description of the Parameter
+ * @param group Description of the Parameter
+ * @exception XMLDBException Description of the Exception
*/
@Override
public void chown(Account u, String group) throws XMLDBException {
@@ -327,7 +365,51 @@ public void chown(Account u, String group) throws XMLDBException {
params.add(u.getName());
params.add(group);
- parent.getClient().execute("setPermissions", params);
+ parent.getClient().execute("chown", params);
+ } catch (final XmlRpcException e) {
+ throw new XMLDBException(ErrorCodes.VENDOR_ERROR, e.getMessage(), e);
+ }
+ }
+
+ /**
+ * Change the owner uid of a resource
+ *
+ * @param res Resource
+ * @param u The new owner of the resource
+ * @exception XMLDBException Description of the Exception
+ */
+ @Override
+ public void chgrp(Resource res, String group) throws XMLDBException {
+ //TODO : use dedicated function in XmldbURI
+ final String path = ((RemoteCollection) res.getParentCollection()).getPath() + "/" + res.getId();
+ try {
+ final List<Object> params = new ArrayList<Object>(4);
+ params.add(path);
+ params.add(group);
+
+ parent.getClient().execute("chgrp", params);
+ } catch (final XmlRpcException e) {
+ throw new XMLDBException(ErrorCodes.VENDOR_ERROR, e.getMessage(), e);
+ }
+ }
+
+ /**
+ * Change the owner uid of a resource
+ *
+ * @param res Resource
+ * @param u The new owner of the resource
+ * @exception XMLDBException Description of the Exception
+ */
+ @Override
+ public void chown(Resource res, Account u) throws XMLDBException {
+ //TODO : use dedicated function in XmldbURI
+ final String path = ((RemoteCollection) res.getParentCollection()).getPath() + "/" + res.getId();
+ try {
+ final List<Object> params = new ArrayList<Object>(4);
+ params.add(path);
+ params.add(u.getName());
+
+ parent.getClient().execute("chown", params);
} catch (final XmlRpcException e) {
throw new XMLDBException(ErrorCodes.VENDOR_ERROR, e.getMessage(), e);
}
@@ -351,7 +433,7 @@ public void chown(Resource res, Account u, String group) throws XMLDBException {
params.add(u.getName());
params.add(group);
- parent.getClient().execute("setPermissions", params);
+ parent.getClient().execute("chown", params);
} catch (final XmlRpcException e) {
throw new XMLDBException(ErrorCodes.VENDOR_ERROR, e.getMessage(), e);
}
@@ -532,35 +614,30 @@ public Permission getPermissions(Resource res) throws XMLDBException {
throw new XMLDBException(ErrorCodes.INVALID_RESOURCE, "resource is null");
}
- Permission perm = ((EXistResource)res).getPermissions();
+ //TODO : use dedicated function in XmldbURI
+ final String path = ((RemoteCollection) res.getParentCollection()).getPath() + "/" + res.getId();
+ try {
+ final List<Object> params = new ArrayList<Object>(1);
+ params.add(path);
- if(perm == null) {
- //TODO : use dedicated function in XmldbURI
- final String path = ((RemoteCollection) res.getParentCollection()).getPath() + "/" + res.getId();
- try {
- final List<Object> params = new ArrayList<Object>(1);
- params.add(path);
+ final HashMap<?,?> result = (HashMap<?,?>) parent.getClient().execute("getPermissions", params);
- final HashMap<?,?> result = (HashMap<?,?>) parent.getClient().execute("getPermissions", params);
+ final String owner = (String)result.get("owner");
+ final String group = (String)result.get("group");
+ final int mode = ((Integer)result.get("permissions")).intValue();
+ final Object[] acl = (Object[])result.get("acl");
+ List aces = null;
+ if(acl != null) {
+ aces = Arrays.asList(acl);
+ }
- final String owner = (String)result.get("owner");
- final String group = (String)result.get("group");
- final int mode = ((Integer)result.get("permissions")).intValue();
- final Object[] acl = (Object[])result.get("acl");
- List aces = null;
- if (acl != null)
- {aces = Arrays.asList(acl);}
+ return getPermission(owner, group, mode, (List<ACEAider>)aces);
- perm = getPermission(owner, group, mode, (List<ACEAider>)aces);
-
- } catch (final XmlRpcException e) {
- throw new XMLDBException(ErrorCodes.VENDOR_ERROR, e.getMessage(), e);
- } catch(final PermissionDeniedException pde) {
- throw new XMLDBException(ErrorCodes.PERMISSION_DENIED, pde.getMessage(), pde);
- }
+ } catch (final XmlRpcException e) {
+ throw new XMLDBException(ErrorCodes.VENDOR_ERROR, e.getMessage(), e);
+ } catch(final PermissionDeniedException pde) {
+ throw new XMLDBException(ErrorCodes.PERMISSION_DENIED, pde.getMessage(), pde);
}
-
- return perm;
}
@Override
View
59 src/org/exist/xmldb/UserManagementService.java
@@ -64,26 +64,61 @@
//public void setPermissions(Collection collection, String owner, String group, int mode) throws XMLDBException;
//public void setPermissions(Resource resource, String owner, String group, int mode) throws XMLDBException;
-
+
/**
- * Change owner and group of the current collection.
+ * Change owner gid of the current collection.
*
- *@param u Description of the Parameter
- *@param group Description of the Parameter
- *@exception XMLDBException Description of the Exception
+ * @param group The group
+ * @throws XMLDBException
*/
- public void chown( Account u, String group ) throws XMLDBException;
+ public void chgrp(String group) throws XMLDBException;
+ /**
+ * Change owner uid of the current collection.
+ *
+ * @param u The user
+ * @throws XMLDBException
+ */
+ public void chown(Account u) throws XMLDBException;
/**
- * Change owner and group of the specified resource.
+ * Change owner uid and gid of the current collection.
*
- *@param res Description of the Parameter
- *@param u Description of the Parameter
- *@param group Description of the Parameter
- *@exception XMLDBException Description of the Exception
+ * @param u The user
+ * @param group The group
+ * @throws XMLDBException
+ */
+ public void chown(Account u, String group) throws XMLDBException;
+
+ /**
+ * Change owner gid of the specified resource.
+ *
+ * @param res The resource
+ * @param group The group
+ * @throws XMLDBException
+ */
+ public void chgrp(Resource res, String group)
+ throws XMLDBException;
+
+ /**
+ * Change owner uid of the specified resource.
+ *
+ * @param res The resource
+ * @param u The user
+ * @throws XMLDBException
+ */
+ public void chown(Resource res, Account u)
+ throws XMLDBException;
+
+ /**
+ * Change owner uid and gid of the specified resource.
+ *
+ * @param res The resource
+ * @param u The user
+ * @param group The group
+ * @throws XMLDBException
*/
- public void chown( Resource res, Account u, String group )
+ public void chown(Resource res, Account u, String group)
throws XMLDBException;
View
36 src/org/exist/xmlrpc/RpcAPI.java
@@ -786,19 +786,29 @@ boolean setPermissions(
int permissions)
throws EXistException, PermissionDeniedException, URISyntaxException;
- boolean setPermissions(
- final String resource,
- final String owner,
- final String ownerGroup,
- final int mode,
- final List<ACEAider> aces)
- throws EXistException, PermissionDeniedException, URISyntaxException;
-
- public boolean setPermissions(
- final String resource,
- final String owner,
- final String ownerGroup)
- throws EXistException, PermissionDeniedException, URISyntaxException;
+ boolean setPermissions(
+ final String resource,
+ final String owner,
+ final String ownerGroup,
+ final int mode,
+ final List<ACEAider> aces)
+ throws EXistException, PermissionDeniedException, URISyntaxException;
+
+ public boolean chgrp(
+ final String resource,
+ final String ownerGroup)
+ throws EXistException, PermissionDeniedException, URISyntaxException;
+
+ public boolean chown(
+ final String resource,
+ final String owner)
+ throws EXistException, PermissionDeniedException, URISyntaxException;
+
+ public boolean chown(
+ final String resource,
+ final String owner,
+ final String ownerGroup)
+ throws EXistException, PermissionDeniedException, URISyntaxException;
public boolean lockResource(String path, String userName)
throws EXistException, PermissionDeniedException, URISyntaxException;
View
38 src/org/exist/xmlrpc/RpcConnection.java
@@ -3744,7 +3744,43 @@ private String retrieveAllAsString(int resultId, HashMap<String, Object> paramet
}
@Override
- public boolean setPermissions(final String resource, final String owner, final String ownerGroup) throws EXistException, PermissionDeniedException, URISyntaxException {
+ public boolean chgrp(final String resource, final String ownerGroup) throws EXistException, PermissionDeniedException, URISyntaxException {
+ executeWithBroker(new BrokerOperation<Void>() {
+ @Override
+ public Void withBroker(final DBBroker broker) throws EXistException, URISyntaxException, PermissionDeniedException {
+ PermissionFactory.updatePermissions(broker, XmldbURI.xmldbUriFor(resource), new PermissionModifier(){
+ @Override
+ public void modify(Permission permission) throws PermissionDeniedException {
+ permission.setGroup(ownerGroup);
+ }
+ });
+ return null;
+ }
+ });
+
+ return true;
+ }
+
+ @Override
+ public boolean chown(final String resource, final String owner) throws EXistException, PermissionDeniedException, URISyntaxException {
+ executeWithBroker(new BrokerOperation<Void>() {
+ @Override
+ public Void withBroker(final DBBroker broker) throws EXistException, URISyntaxException, PermissionDeniedException {
+ PermissionFactory.updatePermissions(broker, XmldbURI.xmldbUriFor(resource), new PermissionModifier(){
+ @Override
+ public void modify(Permission permission) throws PermissionDeniedException {
+ permission.setOwner(owner);
+ }
+ });
+ return null;
+ }
+ });
+
+ return true;
+ }
+
+ @Override
+ public boolean chown(final String resource, final String owner, final String ownerGroup) throws EXistException, PermissionDeniedException, URISyntaxException {
executeWithBroker(new BrokerOperation<Void>() {
@Override
public Void withBroker(final DBBroker broker) throws EXistException, URISyntaxException, PermissionDeniedException {
View
6 test/src/org/exist/dom/DocumentImplTest.java
@@ -53,7 +53,7 @@ public void copyOf_calls_getMetadata() {
other.setMetadata(otherMetadata);
//actions
- doc.copyOf(other);
+ doc.copyOf(other, false);
verify(mockBrokerPool, mockDatabase, mockCurrentSubject, mockCurrentSubjectGroup, mockSecurityManager);
@@ -91,7 +91,7 @@ public void copyOf_calls_metadata_copyOf() {
other.setMetadata(otherMetadata);
//actions
- doc.copyOf(other);
+ doc.copyOf(other, false);
verify(mockBrokerPool, mockDatabase, mockCurrentSubject, mockCurrentSubjectGroup, mockSecurityManager);
@@ -131,7 +131,7 @@ public void copyOf_updates_metadata_created_and_lastModified() {
other.setMetadata(otherMetadata);
//actions
- doc.copyOf(other);
+ doc.copyOf(other, false);
verify(mockBrokerPool, mockDatabase, mockCurrentSubject, mockCurrentSubjectGroup, mockSecurityManager);
View
1,214 test/src/org/exist/security/XMLDBSecurityTest.java
@@ -4,6 +4,7 @@
import org.exist.jetty.JettyStart;
import org.exist.security.internal.aider.GroupAider;
import org.exist.security.internal.aider.UserAider;
+import org.exist.xmldb.CollectionManagementServiceImpl;
import org.exist.xmldb.UserManagementService;
import org.exist.xmldb.XPathQueryServiceImpl;
import org.junit.After;
@@ -93,8 +94,10 @@ public void worldChownCollection() throws XMLDBException {
ums.chown(guest, "guest");
}
+ /**
+ * only the owner or dba can chown a collection or resource
+ */
@Test (expected=XMLDBException.class)
- // only the owner or dba can chown a collection or resource
public void worldChownResource() throws XMLDBException {
final Collection test = DatabaseManager.getCollection(baseUri + "/db/securityTest1", "guest", "guest");
final Resource resource = test.getResource("test.xml");
@@ -140,7 +143,7 @@ public void groupRemoveCollection_canWriteParent() throws XMLDBException {
@Test(expected=XMLDBException.class)
public void groupChmodCollection_asNotOwnerAndNotDBA() throws XMLDBException {
-
+
final Collection test = DatabaseManager.getCollection(baseUri + "/db/securityTest1", "test2", "test2");
final UserManagementService ums = (UserManagementService)test.getService("UserManagementService", "1.0");
@@ -176,127 +179,394 @@ public void groupChmodResource_asOwner() throws XMLDBException {
ums.chmod(resource, 0777);
}
+ /**
+ * DBA can change the owner uid of a collection
+ *
+ * As the user 'admin' (who is a DBA) attempt to change the
+ * ownership uid of /db/securityTest1
+ * to 'test2' user
+ */
+ @Test
+ public void dbaChownUidCollection() throws XMLDBException {
+ final Collection test = DatabaseManager.getCollection(baseUri + "/db/securityTest1", "admin", "");
+ final UserManagementService ums = (UserManagementService)test.getService("UserManagementService", "1.0");
+
+ // attempt to change uid ownership of /db/securityTest1 to the test2 user
+ final Account test2 = ums.getAccount("test2");
+ ums.chown(test2);
+ }
+
+ /**
+ * DBA can change the owner gid of a collection
+ *
+ * As the user 'admin' (who is a DBA) attempt to change the
+ * ownership gid of /db/securityTest1
+ * to 'guest' group
+ */
+ @Test
+ public void dbaChownGidCollection() throws XMLDBException {
+ final Collection test = DatabaseManager.getCollection(baseUri + "/db/securityTest1", "admin", "");
+ final UserManagementService ums = (UserManagementService)test.getService("UserManagementService", "1.0");
+
+ // attempt to change uid ownership of /db/securityTest1 to the guest group
+ ums.chgrp("guest");
+ }
+
+ /**
+ * Owner can NOT change the owner uid of a collection
+ *
+ * As the user 'test1' attempt to change the
+ * ownership uid of /db/securityTest1
+ * to 'test2' user
+ */
+ @Test(expected=XMLDBException.class)
+ public void ownerChownUidCollection() throws XMLDBException {
+ final Collection test = DatabaseManager.getCollection(baseUri + "/db/securityTest1", "test1", "test1");
+ final UserManagementService ums = (UserManagementService)test.getService("UserManagementService", "1.0");
+
+ // attempt to change uid ownership of /db/securityTest1 to the test2 user
+ final Account test2 = ums.getAccount("test2");
+ ums.chown(test2);
+ }
+
+ /**
+ * Owner can NOT change the owner gid of a collection
+ * to a group of which they are not a member
+ *
+ * As the user 'test1' attempt to change the
+ * ownership gid of /db/securityTest1
+ * to 'guest' group
+ */
@Test(expected=XMLDBException.class)
- // only the owner or admin can chown a collection or resource
- public void groupChownCollection() throws XMLDBException {
+ public void ownerChownGidCollection() throws XMLDBException {
+ final Collection test = DatabaseManager.getCollection(baseUri + "/db/securityTest1", "test1", "test1");
+ final UserManagementService ums = (UserManagementService)test.getService("UserManagementService", "1.0");
+
+ // attempt to change gid ownership of /db/securityTest1 to the guest group
+ ums.chgrp("guest");
+ }
+
+ /**
+ * Group member can NOT change the owner uid of a collection
+ *
+ * As the user 'test2' attempt to change the
+ * ownership uid of /db/securityTest1
+ * to ourselves
+ */
+ @Test(expected=XMLDBException.class)
+ public void groupMemberChownUidCollection() throws XMLDBException {
final Collection test = DatabaseManager.getCollection(baseUri + "/db/securityTest1", "test2", "test2");
final UserManagementService ums = (UserManagementService)test.getService("UserManagementService", "1.0");
- // grant myself all rights ;-)
+
+ // attempt to take uid ownership of /db/securityTest1
final Account test2 = ums.getAccount("test2");
- ums.chown(test2, "users");
+ ums.chown(test2);
+ }
+
+ /**
+ * Owner can change the owner gid of a collection
+ * to a group of which they are a member
+ *
+ * As the user 'test1' (who is the owner and
+ * who is in the group 'extusers')
+ * attempt to change ownership gid of /db/securityTest1
+ * to the group 'extusers'
+ */
+ @Test
+ public void ownerAndGroupMemberChownGidCollection() throws XMLDBException {
+ final Collection test = DatabaseManager.getCollection(baseUri + "/db/securityTest1", "test1", "test1");
+ final UserManagementService ums = (UserManagementService)test.getService("UserManagementService", "1.0");
+
+ // attempt to take gid ownership of /db/securityTest1
+ ums.chgrp("extusers");
+
final Permission perms = ums.getPermissions(test);
- assertEquals("test2", perms.getOwner().getName());
+ assertEquals("extusers", perms.getGroup().getName());
}
+
+ /**
+ * Group Member can NOT change the owner gid of a resource
+ * to a group of which they are a member
+ *
+ * As the user 'test2' (who is in the group users)
+ * attempt to change ownership gid of /db/securityTest1/test.xml (which has gid 'users')
+ * to the group 'users' (of which they are a member)
+ */
+ @Test(expected=XMLDBException.class)
+ public void groupMemberChownGidCollection() throws XMLDBException {
+ final Collection test = DatabaseManager.getCollection(baseUri + "/db/securityTest1", "test2", "test2");
+ final UserManagementService ums = (UserManagementService)test.getService("UserManagementService", "1.0");
+ // attempt to take gid ownership of /db/securityTest1/test.xml
+ ums.chgrp("users");
+ }
+
+ /**
+ * Group Member can NOT change owner gid of a collection
+ * to a group of which we are NOT a member
+ *
+ * As the user 'test2' (who is in the group users)
+ * attempt to change ownership gid of /db/securityTest1
+ * to the group 'guest' (of which they are NOT a member)
+ */
@Test(expected=XMLDBException.class)
- // only the owner or admin can chown a collection or resource
- public void groupChownResource() throws XMLDBException {
+ public void groupNonMemberChownGidCollection() throws XMLDBException {
final Collection test = DatabaseManager.getCollection(baseUri + "/db/securityTest1", "test2", "test2");
+ final UserManagementService ums = (UserManagementService)test.getService("UserManagementService", "1.0");
+
+ // attempt to take gid ownership of /db/securityTest1
+ ums.chgrp("guest");
+ }
+
+ /**
+ * DBA can change the owner uid of a resource
+ *
+ * As the user 'admin' (who is a DBA) attempt to change the
+ * ownership uid of /db/securityTest1/test.xml
+ * to 'test2' user
+ */
+ @Test
+ public void dbaChownUidResource() throws XMLDBException {
+ final Collection test = DatabaseManager.getCollection(baseUri + "/db/securityTest1", "admin", "");
final Resource resource = test.getResource("test.xml");
final UserManagementService ums = (UserManagementService)test.getService("UserManagementService", "1.0");
- // grant myself all rights ;-)
+
+ // attempt to change uid ownership of /db/securityTest1/test.xml to the test2 user
+ final Account test2 = ums.getAccount("test2");
+ ums.chown(resource, test2);
+ }
+
+ /**
+ * DBA can change the owner gid of a resource
+ *
+ * As the user 'admin' (who is a DBA) attempt to change the
+ * ownership gid of /db/securityTest1/test1.xml
+ * to 'guest' group
+ */
+ @Test
+ public void dbaChownGidResource() throws XMLDBException {
+ final Collection test = DatabaseManager.getCollection(baseUri + "/db/securityTest1", "admin", "");
+ final Resource resource = test.getResource("test.xml");
+ final UserManagementService ums = (UserManagementService)test.getService("UserManagementService", "1.0");
+
+ // attempt to change uid ownership of /db/securityTest1/test.xml to the guest group
+ ums.chgrp(resource, "guest");
+ }
+
+ /**
+ * Owner can NOT change the owner uid of a resource
+ *
+ * As the user 'test1' attempt to change the
+ * ownership uid of /db/securityTest1/test.xml
+ * to 'test2' user
+ */
+ @Test(expected=XMLDBException.class)
+ public void ownerChownUidResource() throws XMLDBException {
+ final Collection test = DatabaseManager.getCollection(baseUri + "/db/securityTest1", "test1", "test1");
+ final Resource resource = test.getResource("test.xml");
+ final UserManagementService ums = (UserManagementService)test.getService("UserManagementService", "1.0");
+
+ // attempt to change uid ownership of /db/securityTest1/test.xml to the test2 user
final Account test2 = ums.getAccount("test2");
- ums.chown(resource, test2, "users");
+ ums.chown(resource, test2);
+ }
+
+ /**
+ * Owner can NOT change the owner gid of a resource
+ * to a group of which they are not a member
+ *
+ * As the user 'test1' attempt to change the
+ * ownership gid of /db/securityTest1/test.xml
+ * to 'guest' group
+ */
+ @Test(expected=XMLDBException.class)
+ public void ownerChownGidResource() throws XMLDBException {
+ final Collection test = DatabaseManager.getCollection(baseUri + "/db/securityTest1", "test1", "test1");
+ final Resource resource = test.getResource("test.xml");
+ final UserManagementService ums = (UserManagementService)test.getService("UserManagementService", "1.0");
+
+ // attempt to change gid ownership of /db/securityTest1/test.xml to the guest group
+ ums.chgrp(resource, "guest");
}
+
+ /**
+ * Group member can NOT change the owner uid of a resource
+ *
+ * As the user 'test2' attempt to change the
+ * ownership uid of /db/securityTest1/test.xml
+ * to ourselves
+ */
+ @Test(expected=XMLDBException.class)
+ public void groupMemberChownUidResource() throws XMLDBException {
+ final Collection test = DatabaseManager.getCollection(baseUri + "/db/securityTest1", "test2", "test2");
+ final Resource resource = test.getResource("test.xml");
+ final UserManagementService ums = (UserManagementService)test.getService("UserManagementService", "1.0");
+
+ // attempt to take uid ownership of /db/securityTest1/test.xml
+ final Account test2 = ums.getAccount("test2");
+ ums.chown(resource, test2);
+ }
+
+ /**
+ * Owner can change the owner gid of a resource
+ * to a group of which they are a member
+ *
+ * As the user 'test1' (who is the owner and
+ * who is in the group 'extusers')
+ * attempt to change ownership gid of /db/securityTest1/test.xml
+ * to the group 'extusers'
+ */
+ @Test
+ public void ownerAndGroupMemberChownGidResource() throws XMLDBException {
+ final Collection test = DatabaseManager.getCollection(baseUri + "/db/securityTest1", "test1", "test1");
+ final Resource resource = test.getResource("test.xml");
+ final UserManagementService ums = (UserManagementService)test.getService("UserManagementService", "1.0");
+
+ // attempt to take gid ownership of /db/securityTest1
+ ums.chgrp(resource, "extusers");
+
+ final Permission perms = ums.getPermissions(resource);
+ assertEquals("extusers", perms.getGroup().getName());
+ }
+
+ /**
+ * Group Member can NOT change the owner gid of a resource
+ * to a group of which they are a member
+ *
+ * As the user 'test2' (who is in the group users)
+ * attempt to change ownership gid of /db/securityTest1/test.xml (which has gid 'isers')
+ * to the group 'users' (of which they are a member)
+ */
+ @Test(expected=XMLDBException.class)
+ public void groupMemberChownGidResource() throws XMLDBException {
+ final Collection test = DatabaseManager.getCollection(baseUri + "/db/securityTest1", "test2", "test2");
+ final Resource resource = test.getResource("test.xml");
+ final UserManagementService ums = (UserManagementService)test.getService("UserManagementService", "1.0");
+
+ // attempt to take gid ownership of /db/securityTest1/test.xml
+ ums.chgrp(resource, "users");
+
+ final Permission perms = ums.getPermissions(resource);
+ assertEquals("users", perms.getGroup().getName());
+ }
+
+ /**
+ * Group Member can NOT change owner gid of a resource
+ * to a group of which we are NOT a member
+ *
+ * As the user 'test2' (who is in the group users)
+ * attempt to change ownership gid of /db/securityTest1/test.xml
+ * to the group 'guest' (of which they are NOT a member)
+ */
+ @Test(expected=XMLDBException.class)
+ public void groupNonMemberChownGidResource() throws XMLDBException {
+ final Collection test = DatabaseManager.getCollection(baseUri + "/db/securityTest1", "test2", "test2");
+ final Resource resource = test.getResource("test.xml");
+ final UserManagementService ums = (UserManagementService)test.getService("UserManagementService", "1.0");
+
+ // attempt to take gid ownership of /db/securityTest1/test.xml
+ ums.chgrp(resource, "guest");
+ }
+
@Test
public void onlyExecuteRequiredToOpenCollectionContent() throws XMLDBException {
final Collection test = DatabaseManager.getCollection(baseUri + "/db/securityTest1", "test1", "test1");
final UserManagementService ums = (UserManagementService) test.getService("UserManagementService", "1.0");
-
+
ums.chmod("--x------");
test.close();
-
+
DatabaseManager.getCollection(baseUri + "/db/securityTest1", "test1", "test1");
}
-
+
@Test(expected=XMLDBException.class)
public void cannotOpenCollectionWithoutExecute() throws XMLDBException {
final Collection test = DatabaseManager.getCollection(baseUri + "/db/securityTest1", "test1", "test1");
final UserManagementService ums = (UserManagementService) test.getService("UserManagementService", "1.0");
-
+
ums.chmod("rw-rw-rw-");
test.close();
-
+
DatabaseManager.getCollection(baseUri + "/db/securityTest1", "test1", "test1");
}
-
+
@Test
public void canOpenCollectionWithExecute() throws XMLDBException {
final Collection test = DatabaseManager.getCollection(baseUri + "/db/securityTest1", "test1", "test1");
final UserManagementService ums = (UserManagementService) test.getService("UserManagementService", "1.0");
-
+
ums.chmod("--x--x--x");
test.close();
-
+
DatabaseManager.getCollection(baseUri + "/db/securityTest1", "test1", "test1");
}
-
+
@Test(expected=XMLDBException.class)
public void cannotOpenRootCollectionWithoutExecute() throws XMLDBException {
final Collection test = DatabaseManager.getCollection(baseUri + "/db", "admin", "");
final UserManagementService ums = (UserManagementService) test.getService("UserManagementService", "1.0");
-
+
ums.chmod("rw-rw-rw-");
test.close();
-
+
DatabaseManager.getCollection(baseUri + "/db", "test1", "test1");
}
-
+
@Test
public void canOpenRootCollectionWithExecute() throws XMLDBException {
final Collection test = DatabaseManager.getCollection(baseUri + "/db", "admin", "");
final UserManagementService ums = (UserManagementService) test.getService("UserManagementService", "1.0");
-
+
ums.chmod("--x--x--x");
test.close();
-
+
DatabaseManager.getCollection(baseUri + "/db", "test1", "test1");
}
-
+
@Test
public void onlyReadAndExecuteRequiredToListCollectionResources() throws XMLDBException {
final Collection test = DatabaseManager.getCollection(baseUri + "/db/securityTest1", "test1", "test1");
final UserManagementService ums = (UserManagementService) test.getService("UserManagementService", "1.0");
-
+
ums.chmod("r-x------");
-
+
test.listResources();
}
-
+
@Test(expected=XMLDBException.class)
public void cannotListCollectionResourcesWithoutRead() throws XMLDBException {
Collection test = DatabaseManager.getCollection(baseUri + "/db/securityTest1", "test1", "test1");
final UserManagementService ums = (UserManagementService) test.getService("UserManagementService", "1.0");
-
+
ums.chmod("-wx-wx-wx");
test.close();
-
+
test = DatabaseManager.getCollection(baseUri + "/db/securityTest1", "test1", "test1");
-
+
test.listResources();
}
-
+
@Test
public void onlyReadAndExecuteRequiredToListCollectionSubCollections() throws XMLDBException {
final Collection test = DatabaseManager.getCollection(baseUri + "/db/securityTest1", "test1", "test1");
final UserManagementService ums = (UserManagementService) test.getService("UserManagementService", "1.0");
-
+
ums.chmod("r-x------");
-
+
test.listChildCollections();
}
-
+
@Test(expected=XMLDBException.class)
public void cannotListCollectionSubCollectionsWithoutRead() throws XMLDBException {
Collection test = DatabaseManager.getCollection(baseUri + "/db/securityTest1", "test1", "test1");
final UserManagementService ums = (UserManagementService) test.getService("UserManagementService", "1.0");
-
+
ums.chmod("-wx-wx-wx");
test.close();
-
+
test = DatabaseManager.getCollection(baseUri + "/db/securityTest1", "test1", "test1");
-
+
test.listChildCollections();
}
@@ -304,114 +574,114 @@ public void cannotListCollectionSubCollectionsWithoutRead() throws XMLDBExceptio
public void canReadXmlResourceWithOnlyExecutePermissionOnParentCollection() throws XMLDBException{
Collection test = DatabaseManager.getCollection(baseUri + "/db/securityTest1", "test1", "test1");
final UserManagementService ums = (UserManagementService) test.getService("UserManagementService", "1.0");
-
+
ums.chmod("--x------");
test.close();
-
+
test = DatabaseManager.getCollection(baseUri + "/db/securityTest1", "test1", "test1");
-
+
final Resource resource = test.getResource("test.xml");
assertEquals("<test/>", resource.getContent());
}
-
+
@Test(expected=XMLDBException.class)
public void cannotReadXmlResourceWithoutExecutePermissionOnParentCollection() throws XMLDBException{
Collection test = DatabaseManager.getCollection(baseUri + "/db/securityTest1", "test1", "test1");
final UserManagementService ums = (UserManagementService) test.getService("UserManagementService", "1.0");
-
+
ums.chmod("rw-------");
test.close();
-
+
test = DatabaseManager.getCollection(baseUri + "/db/securityTest1", "test1", "test1");
-
+
final Resource resource = test.getResource("test.xml");
assertEquals("<test/>", resource.getContent());
}
-
+
@Test
public void canReadBinaryResourceWithOnlyExecutePermissionOnParentCollection() throws XMLDBException{
Collection test = DatabaseManager.getCollection(baseUri + "/db/securityTest1", "test1", "test1");
final UserManagementService ums = (UserManagementService) test.getService("UserManagementService", "1.0");
-
+
ums.chmod("--x------");
test.close();
-
+
test = DatabaseManager.getCollection(baseUri + "/db/securityTest1", "test1", "test1");
-
+
final Resource resource = test.getResource("test.bin");
assertArrayEquals("binary-test".getBytes(), (byte[])resource.getContent());
}
-
+
@Test(expected=XMLDBException.class)
public void cannotReadBinaryResourceWithoutExecutePermissionOnParentCollection() throws XMLDBException{
Collection test = DatabaseManager.getCollection(baseUri + "/db/securityTest1", "test1", "test1");
final UserManagementService ums = (UserManagementService) test.getService("UserManagementService", "1.0");
-
+
ums.chmod("rw-------");
test.close();
-
+
test = DatabaseManager.getCollection(baseUri + "/db/securityTest1", "test1", "test1");
-
+
final Resource resource = test.getResource("test.bin");
assertArrayEquals("binary-test".getBytes(), (byte[])resource.getContent());
}
-
+
@Test
public void canReadXmlResourceWithOnlyReadPermission() throws XMLDBException{
Collection test = DatabaseManager.getCollection(baseUri + "/db/securityTest1", "test1", "test1");
final UserManagementService ums = (UserManagementService) test.getService("UserManagementService", "1.0");
-
+
Resource resource = test.getResource("test.xml");
ums.chmod(resource, "r--------");
test.close();
-
+
test = DatabaseManager.getCollection(baseUri + "/db/securityTest1", "test1", "test1");
-
+
resource = test.getResource("test.xml");
assertEquals("<test/>", resource.getContent());
}
-
+
@Test(expected=XMLDBException.class)
public void cannotReadXmlResourceWithoutReadPermission() throws XMLDBException{
Collection test = DatabaseManager.getCollection(baseUri + "/db/securityTest1", "test1", "test1");
final UserManagementService ums = (UserManagementService) test.getService("UserManagementService", "1.0");
-
+
Resource resource = test.getResource("test.xml");
ums.chmod(resource, "-wx------");
test.close();
-
+
test = DatabaseManager.getCollection(baseUri + "/db/securityTest1", "test1", "test1");
-
+
resource = test.getResource("test.xml");
assertEquals("<test/>", resource.getContent());
}
-
+
@Test
public void canReadBinaryResourceWithOnlyReadPermission() throws XMLDBException{
Collection test = DatabaseManager.getCollection(baseUri + "/db/securityTest1", "test1", "test1");
final UserManagementService ums = (UserManagementService) test.getService("UserManagementService", "1.0");
-
+
Resource resource = test.getResource("test.bin");
ums.chmod(resource, "r--------");
test.close();
-
+
test = DatabaseManager.getCollection(baseUri + "/db/securityTest1", "test1", "test1");
-
+
resource = test.getResource("test.bin");
assertArrayEquals("binary-test".getBytes(), (byte[])resource.getContent());
}
-
+
@Test(expected=XMLDBException.class)
public void cannotReadBinaryResourceWithoutReadPermission() throws XMLDBException{
Collection test = DatabaseManager.getCollection(baseUri + "/db/securityTest1", "test1", "test1");
final UserManagementService ums = (UserManagementService) test.getService("UserManagementService", "1.0");
-
+
Resource resource = test.getResource("test.bin");
ums.chmod(resource, "-wx------");
test.close();
-
+
test = DatabaseManager.getCollection(baseUri + "/db/securityTest1", "test1", "test1");
-
+
resource = test.getResource("test.bin");
assertArrayEquals("binary-test".getBytes(), (byte[])resource.getContent());
}
@@ -420,99 +690,99 @@ public void cannotReadBinaryResourceWithoutReadPermission() throws XMLDBExceptio
public void canCreateXmlResourceWithOnlyExecuteAndWritePermissionOnParentCollection() throws XMLDBException{
Collection test = DatabaseManager.getCollection(baseUri + "/db/securityTest1", "test1", "test1");
final UserManagementService ums = (UserManagementService) test.getService("UserManagementService", "1.0");
-
+
ums.chmod("-wx------");
test.close();
-
+
test = DatabaseManager.getCollection(baseUri + "/db/securityTest1", "test1", "test1");
-
+
final Resource resource = test.createResource("other.xml", XMLResource.RESOURCE_TYPE);
resource.setContent("<other/>");
test.storeResource(resource);
}
-
+
@Test
public void canCreateBinaryResourceWithOnlyExecuteAndWritePermissionOnParentCollection() throws XMLDBException{
Collection test = DatabaseManager.getCollection(baseUri + "/db/securityTest1", "test1", "test1");
final UserManagementService ums = (UserManagementService) test.getService("UserManagementService", "1.0");
-
+
ums.chmod("-wx------");
test.close();
-
+
test = DatabaseManager.getCollection(baseUri + "/db/securityTest1", "test1", "test1");
-
+
final Resource resource = test.createResource("other.bin", BinaryResource.RESOURCE_TYPE);
resource.setContent("binary".getBytes());
test.storeResource(resource);
}
-
+
@Test
public void canUpdateXmlResourceWithOnlyExecutePermissionOnParentCollection() throws XMLDBException{
Collection test = DatabaseManager.getCollection(baseUri + "/db/securityTest1", "test1", "test1");
final UserManagementService ums = (UserManagementService) test.getService("UserManagementService", "1.0");
-
+
ums.chmod("--x------");
test.close();
-
+
test = DatabaseManager.getCollection(baseUri + "/db/securityTest1", "test1", "test1");
-
+
Resource resource = test.getResource("test.xml");
assertEquals("<test/>", resource.getContent());
-
+
//update the resource
resource.setContent("<testing/>");
test.storeResource(resource);
-
+
resource = test.getResource("test.xml");
assertEquals("<testing/>", resource.getContent());
}
-
+
@Test
public void canUpdateBinaryResourceWithOnlyExecutePermissionOnParentCollection() throws XMLDBException{
Collection test = DatabaseManager.getCollection(baseUri + "/db/securityTest1", "test1", "test1");
final UserManagementService ums = (UserManagementService) test.getService("UserManagementService", "1.0");
-
+
ums.chmod("--x------");
test.close();
-
+
test = DatabaseManager.getCollection(baseUri + "/db/securityTest1", "test1", "test1");
-
+
Resource resource = test.getResource("test.bin");
assertArrayEquals("binary-test".getBytes(), (byte[])resource.getContent());
-
+
//update the resource
resource.setContent("testing".getBytes());
test.storeResource(resource);
-
+
resource = test.getResource("test.bin");
assertArrayEquals("testing".getBytes(), (byte[])resource.getContent());
}
-
+
@Test
public void canExecuteXQueryWithOnlyExecutePermissionOnParentCollection() throws XMLDBException{
Collection test = DatabaseManager.getCollection(baseUri + "/db/securityTest1", "test1", "test1");
final UserManagementService ums = (UserManagementService) test.getService("UserManagementService", "1.0");
-
+
final String xquery = "<xquery>{ 1 + 1 }</xquery>";
- Resource xqueryResource = test.createResource("test.xquery", "BinaryResource");
+ Resource xqueryResource = test.createResource("test.xquery", BinaryResource.RESOURCE_TYPE);
xqueryResource.setContent(xquery);
test.storeResource(xqueryResource);
-
+
ums.chmod("--x------");
ums.chmod(xqueryResource, "rwx------"); //set execute bit on xquery (its off by default!)
test.close();
-
+
test = DatabaseManager.getCollection(baseUri + "/db/securityTest1", "test1", "test1");
-
+
xqueryResource = test.getResource("test.xquery");
assertEquals(xquery, new String((byte[])xqueryResource.getContent()));
-
+
//execute the stored XQuery
final XPathQueryServiceImpl queryService = (XPathQueryServiceImpl)test.getService("XPathQueryService", "1.0");
final ResourceSet result = queryService.executeStoredQuery("/db/securityTest1/test.xquery");
assertEquals("<xquery>2</xquery>", result.getResource(0).getContent());
}
-
+
/**
* Note the eventual goal is for XQuery to be executeable in eXist
* with just the EXECUTE flag set, this however will require some
@@ -524,50 +794,650 @@ public void canExecuteXQueryWithOnlyExecutePermissionOnParentCollection() throws
public void canExecuteXQueryWithOnlyExecuteAndReadPermission() throws XMLDBException{
Collection test = DatabaseManager.getCollection(baseUri + "/db/securityTest1", "test1", "test1");
final UserManagementService ums = (UserManagementService) test.getService("UserManagementService", "1.0");
-
+
final String xquery = "<xquery>{ 1 + 2 }</xquery>";
- Resource xqueryResource = test.createResource("test.xquery", "BinaryResource");
+ Resource xqueryResource = test.createResource("test.xquery", BinaryResource.RESOURCE_TYPE);
xqueryResource.setContent(xquery);
test.storeResource(xqueryResource);
-
+
ums.chmod(xqueryResource, "r-x------"); //execute only on xquery
test.close();
-
+
test = DatabaseManager.getCollection(baseUri + "/db/securityTest1", "test1", "test1");
-
+
xqueryResource = test.getResource("test.xquery");
assertEquals(xquery, new String((byte[])xqueryResource.getContent()));
-
+
//execute the stored XQuery
final XPathQueryServiceImpl queryService = (XPathQueryServiceImpl)test.getService("XPathQueryService", "1.0");
final ResourceSet result = queryService.executeStoredQuery("/db/securityTest1/test.xquery");
assertEquals("<xquery>3</xquery>", result.getResource(0).getContent());
}
-
+
@Test(expected=XMLDBException.class)
public void cannotExecuteXQueryWithoutExecutePermission() throws XMLDBException{
Collection test = DatabaseManager.getCollection(baseUri + "/db/securityTest1", "test1", "test1");
final UserManagementService ums = (UserManagementService) test.getService("UserManagementService", "1.0");
-
+
final String xquery = "<xquery>{ 1 + 2 }</xquery>";
- Resource xqueryResource = test.createResource("test.xquery", "BinaryResource");
+ Resource xqueryResource = test.createResource("test.xquery", BinaryResource.RESOURCE_TYPE);
xqueryResource.setContent(xquery);
test.storeResource(xqueryResource);
-
+
ums.chmod(xqueryResource, "rw-------"); //execute only on xquery
test.close();
-
+
test = DatabaseManager.getCollection(baseUri + "/db/securityTest1", "test1", "test1");
-
+
xqueryResource = test.getResource("test.xquery");
assertEquals(xquery, new String((byte[])xqueryResource.getContent()));
-
+
//execute the stored XQuery
final XPathQueryServiceImpl queryService = (XPathQueryServiceImpl)test.getService("XPathQueryService", "1.0");
final ResourceSet result = queryService.executeStoredQuery("/db/securityTest1/test.xquery");
assertEquals("<xquery>3</xquery>", result.getResource(0).getContent());
}
-
+
+ @Test(expected=XMLDBException.class)
+ public void cannotOpenCollection() throws XMLDBException {
+ //check that a user not in the users group (i.e. test3) cannot open the collection /db/securityTest1
+ DatabaseManager.getCollection(baseUri + "/db/securityTest1", "test3", "test3");
+ }
+
+ @Test
+ public void canOpenCollection() throws XMLDBException {
+ //check that a user in the users group (i.e. test2) can open the collection /db/securityTest1
+ DatabaseManager.getCollection(baseUri + "/db/securityTest1", "test1", "test1");
+ DatabaseManager.getCollection(baseUri + "/db/securityTest1", "test2", "test2");
+
+ //check that any user can open the collection /db/securityTest3
+ DatabaseManager.getCollection(baseUri + "/db/securityTest3", "test1", "test1");
+ DatabaseManager.getCollection(baseUri + "/db/securityTest3", "test2", "test2");
+ DatabaseManager.getCollection(baseUri + "/db/securityTest3", "test3", "test3");
+ }
+
+ @Test
+ public void copyCollectionWithResources() throws XMLDBException {
+ Collection test = DatabaseManager.getCollection(baseUri + "/db/securityTest3", "test1", "test1");
+ CollectionManagementServiceImpl cms = (CollectionManagementServiceImpl) test.getService("CollectionManagementService", "1.0");
+
+ //create collection owned by "test1", and group "users" in /db/securityTest3
+ Collection source = cms.createCollection("source");
+
+ //create resource owned by "test1", and group "users" in /db/securityTest3/source
+ Resource resSource = source.createResource("source1.xml", XMLResource.RESOURCE_TYPE);
+ resSource.setContent("<test/>");
+ source.storeResource(resSource);
+
+ resSource = source.createResource("source2.xml", XMLResource.RESOURCE_TYPE);
+ resSource.setContent("<test/>");
+ source.storeResource(resSource);
+
+ //as the 'test3' user copy the collection
+ test = DatabaseManager.getCollection(baseUri + "/db/securityTest3", "test3", "test3");
+ cms = (CollectionManagementServiceImpl) test.getService("CollectionManagementService", "1.0");
+ cms.copy("/db/securityTest3/source", "/db/securityTest3", "copy-of-source");
+
+ final Collection copyOfSource = test.getChildCollection("copy-of-source");
+ assertNotNull(copyOfSource);
+ assertEquals(2, copyOfSource.listResources().length);
+ }
+
+ /**
+ * As the 'test1' user, creates the collection and resource:
+ *
+ * test1:users /db/securityTest3/source
+ * test1:users /db/securityTest3/source/source1.xml
+ * test1:users /db/securityTest3/source/source2.xml
+ *
+ * We then also create the Collection
+ * test1:users /db/securityTest3/copy-of-source (0777)
+ * so that the destination (for the copy we are about
+ * to do) already exists and is writable...
+ *
+ * As the 'test3' user, copy the collection:
+ *
+ * /db/securityTest3/source
+ * -> /db/securityTest3/copy-of-source
+ */
+ @Test
+ public void copyCollectionWithResources_destExists_destIsWritable() throws XMLDBException {
+ Collection test = DatabaseManager.getCollection(baseUri + "/db/securityTest3", "test1", "test1");
+ CollectionManagementServiceImpl cms = (CollectionManagementServiceImpl) test.getService("CollectionManagementService", "1.0");
+
+ //create collection owned by "test1", and group "users" in /db/securityTest3
+ Collection source = cms.createCollection("source");
+
+ //create resource owned by "test1", and group "users" in /db/securityTest3/source
+ Resource resSource = source.createResource("source1.xml", XMLResource.RESOURCE_TYPE);
+ resSource.setContent("<test/>");
+ source.storeResource(resSource);
+
+ resSource = source.createResource("source2.xml", XMLResource.RESOURCE_TYPE);
+ resSource.setContent("<test/>");
+ source.storeResource(resSource);
+
+ //pre-create the destination and set writable by all
+ final Collection dest = cms.createCollection("copy-of-source");
+ final UserManagementService ums = (UserManagementService)dest.getService("UserManagementService", "1.0");
+ ums.chmod(0777);
+
+
+ //as the 'test3' user copy the collection
+ test = DatabaseManager.getCollection(baseUri + "/db/securityTest3", "test3", "test3");
+ cms = (CollectionManagementServiceImpl) test.getService("CollectionManagementService", "1.0");
+ cms.copy("/db/securityTest3/source", "/db/securityTest3", "copy-of-source");
+
+ final Collection copyOfSource = test.getChildCollection("copy-of-source");
+ assertNotNull(copyOfSource);
+ assertEquals(2, copyOfSource.listResources().length);
+ }
+
+ /**
+ * As the 'test1' user, creates the collection and resource:
+ *
+ * test1:users /db/securityTest3/source
+ * test1:users /db/securityTest3/source/source1.xml
+ * test1:users /db/securityTest3/source/source2.xml
+ *
+ * We then also create the Collection
+ * test1:users /db/securityTest3/copy-of-source (0755)
+ * so that the destination (for the copy we are about
+ * to do) already exists and is NOT writable...
+ *
+ * As the 'test3' user, copy the collection:
+ *
+ * /db/securityTest3/source
+ * -> /db/securityTest3/copy-of-source
+ */
+ @Test(expected=XMLDBException.class)
+ public void copyCollectionWithResources_destExists_destIsNotWritable() throws XMLDBException {
+ Collection test = DatabaseManager.getCollection(baseUri + "/db/securityTest3", "test1", "test1");
+ CollectionManagementServiceImpl cms = (CollectionManagementServiceImpl) test.getService("CollectionManagementService", "1.0");
+
+ //create collection owned by "test1", and group "users" in /db/securityTest3
+ Collection source = cms.createCollection("source");
+
+ //create resource owned by "test1", and group "users" in /db/securityTest3/source
+ Resource resSource = source.createResource("source1.xml", XMLResource.RESOURCE_TYPE);
+ resSource.setContent("<test/>");
+ source.storeResource(resSource);
+
+ resSource = source.createResource("source2.xml", XMLResource.RESOURCE_TYPE);
+ resSource.setContent("<test/>");
+ source.storeResource(resSource);
+
+ //pre-create the destination with default mode (0755)
+ //so that it is not writable by 'test3' user
+ final Collection dest = cms.createCollection("copy-of-source");
+
+
+ //as the 'test3' user copy the collection
+ test = DatabaseManager.getCollection(baseUri + "/db/securityTest3", "test3", "test3");
+ cms = (CollectionManagementServiceImpl) test.getService("CollectionManagementService", "1.0");
+ cms.copy("/db/securityTest3/source", "/db/securityTest3", "copy-of-source");
+ }
+
+ /**
+ * As the 'test1' user, creates the collection and resource:
+ *
+ * test1:users /db/securityTest3/source
+ * test1:users /db/securityTest3/source/source1.xml
+ * test1:users /db/securityTest3/source/source2.xml
+ *
+ * We then also create the Collection
+ * test1:users /db/securityTest3/copy-of-source (0777)
+ * so that the destination (for the copy we are about
+ * to do) already exists and is writable.
+ * We then create the resource
+ * test1:users /db/securityTest/copy-of-source/source1.xml
+ * and set it so that it is not accessible by anyone
+ * apart from 'test1' user...
+ *
+ * As the 'test3' user, copy the collection:
+ *
+ * /db/securityTest3/source
+ * -> /db/securityTest3/copy-of-source
+ *
+ * The test should prove that during a copy, existing
+ * documents in the dest are replaced as long as the
+ * dest collection has write permission and that the
+ * permissions on the dest resource must also be writable
+ */
+ @Test(expected=XMLDBException.class)
+ public void copyCollectionWithResources_destResourceExists_destResourceIsNotWritable() throws XMLDBException {
+ Collection test = DatabaseManager.getCollection(baseUri + "/db/securityTest3", "test1", "test1");
+ CollectionManagementServiceImpl cms = (CollectionManagementServiceImpl) test.getService("CollectionManagementService", "1.0");
+
+ //create collection owned by "test1", and group "users" in /db/securityTest3
+ Collection source = cms.createCollection("source");
+
+ //create resource owned by "test1", and group "users" in /db/securityTest3/source
+ Resource resSource = source.createResource("source1.xml", XMLResource.RESOURCE_TYPE);
+ resSource.setContent("<test1/>");
+ source.storeResource(resSource);
+
+ resSource = source.createResource("source2.xml", XMLResource.RESOURCE_TYPE);
+ resSource.setContent("<test2/>");
+ source.storeResource(resSource);
+
+ //pre-create the destination and set writable by all
+ final Collection dest = cms.createCollection("copy-of-source");
+ UserManagementService ums = (UserManagementService) dest.getService("UserManagementService", "1.0");
+ ums.chmod(0777);
+
+ //pre-create a destination resource and set no access to group and others
+ Resource resDestSource1 = dest.createResource("source1.xml", XMLResource.RESOURCE_TYPE);
+ resDestSource1.setContent("<old/>");
+ dest.storeResource(resDestSource1);
+ ums.chmod(resDestSource1, 0700);
+
+
+ //as the 'test3' user copy the collection
+ test = DatabaseManager.getCollection(baseUri + "/db/securityTest3", "test3", "test3");
+ cms = (CollectionManagementServiceImpl) test.getService("CollectionManagementService", "1.0");
+ cms.copy("/db/securityTest3/source", "/db/securityTest3", "copy-of-source");
+
+ final Collection copyOfSource = test.getChildCollection("copy-of-source");
+ assertNotNull(copyOfSource);
+ assertEquals(2, copyOfSource.listResources().length);
+
+ final Resource resCopyOfSource1 = copyOfSource.getResource("source1.xml");
+ assertEquals("<test1/>", resCopyOfSource1.getContent().toString());
+
+ final Resource resCopyOfSource2 = copyOfSource.getResource("source2.xml");
+ assertEquals("<test2/>", resCopyOfSource2.getContent().toString());
+
+ //TODO check perms are/areNot preserved? on the replaced resource
+ }
+
+ @Test
+ public void copyCollectionWithResources_withSubCollectionWithResource() throws XMLDBException {
+ Collection test = DatabaseManager.getCollection(baseUri + "/db/securityTest3", "test1", "test1");
+ CollectionManagementServiceImpl cms = (CollectionManagementServiceImpl) test.getService("CollectionManagementService", "1.0");
+
+ //create collection owned by "test1", and group "users" in /db/securityTest3
+ Collection source = cms.createCollection("source");
+
+ //create resource owned by "test1", and group "users" in /db/securityTest3/source
+ Resource resSource = source.createResource("source1.xml", XMLResource.RESOURCE_TYPE);
+ resSource.setContent("<test/>");
+ source.storeResource(resSource);
+
+ resSource = source.createResource("source2.xml", XMLResource.RESOURCE_TYPE);
+ resSource.setContent("<test/>");
+ source.storeResource(resSource);
+
+ //create sub-collection "sub" owned by "test1", and group "users" in /db/securityTest3/source
+ CollectionManagementService cms1 = (CollectionManagementServiceImpl)source.getService("CollectionManagementService", "1.0");
+ Collection sub = cms1.createCollection("sub");
+
+ //create resource owned by "test1", and group "users" in /db/securityTest3/source/sub1
+ Resource resSub = sub.createResource("sub1.xml", XMLResource.RESOURCE_TYPE);
+ resSub.setContent("<test-sub/>");
+ sub.storeResource(resSub);
+
+ //as the 'test3' user copy the collection
+ test = DatabaseManager.getCollection(baseUri + "/db/securityTest3", "test3", "test3");
+ cms = (CollectionManagementServiceImpl) test.getService("CollectionManagementService", "1.0");
+ cms.copy("/db/securityTest3/source", "/db/securityTest3", "copy-of-source");
+
+ final Collection copyOfSource = test.getChildCollection("copy-of-source");
+ assertNotNull(copyOfSource);
+ assertEquals(2, copyOfSource.listResources().length);
+
+ final Collection copyOfSub = copyOfSource.getChildCollection("sub");
+ assertNotNull(copyOfSub);
+ assertEquals(1, copyOfSub.listResources().length);
+ }
+
+ @Test
+ public void copyDocument_doesNotPreservePermissions() throws XMLDBException {
+ Collection test = DatabaseManager.getCollection(baseUri + "/db/securityTest3", "test1", "test1");
+ CollectionManagementServiceImpl cms = (CollectionManagementServiceImpl) test.getService("CollectionManagementService", "1.0");
+
+ //create resource owned by "test1", and group "users" in /db/securityTest3
+ final Resource resSource = test.createResource("source.xml", XMLResource.RESOURCE_TYPE);
+ resSource.setContent("<test/>");
+ test.storeResource(resSource);
+
+ //as the 'test3' user copy the resource
+ test = DatabaseManager.getCollection(baseUri + "/db/securityTest3", "test3", "test3");
+ cms = (CollectionManagementServiceImpl) test.getService("CollectionManagementService", "1.0");
+ cms.copyResource("/db/securityTest3/source.xml", "/db/securityTest3", "copy-of-source.xml");
+
+ final UserManagementService ums = (UserManagementService) test.getService("UserManagementService", "1.0");
+ final Permission permissions = ums.getPermissions(test.getResource("copy-of-source.xml"));
+
+ //resource should be owned by test3:guest, i.e. permissions were not preserved from the test1 users doc /db/securityTest3/source.xml
+ assertEquals("test3", permissions.getOwner().getName());
+ assertEquals("guest", permissions.getGroup().getName());
+ }
+
+ @Test
+ public void copyDocument_doesPreservePermissions_whenDestResourceExists() throws XMLDBException {
+ Collection test = DatabaseManager.getCollection(baseUri + "/db/securityTest3", "test1", "test1");
+ CollectionManagementServiceImpl cms = (CollectionManagementServiceImpl) test.getService("CollectionManagementService", "1.0");
+
+ //create resource owned by "test1", and group "users" in /db/securityTest3
+ final Resource resSource = test.createResource("source.xml", XMLResource.RESOURCE_TYPE);
+ resSource.setContent("<test/>");
+ test.storeResource(resSource);
+
+ //pre-create the dest resource (before the copy) and set writable by all
+ final Resource resDest = test.createResource("copy-of-source.xml", XMLResource.RESOURCE_TYPE);
+ resDest.setContent("<old/>");
+ test.storeResource(resDest);
+ UserManagementService ums = (UserManagementService) test.getService("UserManagementService", "1.0");
+ ums.chmod(resDest, 0777);
+
+
+ //as the 'test3' user copy the resource
+ test = DatabaseManager.getCollection(baseUri + "/db/securityTest3", "test3", "test3");
+ cms = (CollectionManagementServiceImpl) test.getService("CollectionManagementService", "1.0");
+ cms.copyResource("/db/securityTest3/source.xml", "/db/securityTest3", "copy-of-source.xml");
+
+ //as test3 user!
+ ums = (UserManagementService) test.getService("UserManagementService", "1.0");
+ final Permission permissions = ums.getPermissions(test.getResource("copy-of-source.xml"));
+
+ //resource should be owned by test3:guest, i.e. permissions were not preserved from the test1 users doc /db/securityTest3/source.xml
+ assertEquals("test1", permissions.getOwner().getName());
+ assertEquals("users", permissions.getGroup().getName());
+
+ //TODO copy collection should do the same??!?
+ }
+
+ @Test
+ public void copyCollection_doesNotPreservePermissions() throws XMLDBException {
+ Collection test = DatabaseManager.getCollection(baseUri + "/db/securityTest3", "test1", "test1");
+ CollectionManagementServiceImpl cms = (CollectionManagementServiceImpl) test.getService("CollectionManagementService", "1.0");
+
+ //create collection owned by "test1", and group "users" in /db/securityTest3
+ Collection source = cms.createCollection("source");
+
+ //as the 'test3' user copy the collection
+ test = DatabaseManager.getCollection(baseUri + "/db/securityTest3", "test3", "test3");
+ cms = (CollectionManagementServiceImpl) test.getService("CollectionManagementService", "1.0");
+ cms.copy("/db/securityTest3/source", "/db/securityTest3", "copy-of-source");
+
+
+ final UserManagementService ums = (UserManagementService) test.getService("UserManagementService", "1.0");
+ final Permission permissions = ums.getPermissions(test.getChildCollection("copy-of-source"));
+
+ //collection should be owned by test3:guest, i.e. permissions were not preserved from the test1 users collection /db/securityTest3/source
+ assertEquals("test3", permissions.getOwner().getName());
+ assertEquals("guest", permissions.getGroup().getName());
+ }
+
+ @Test
+ public void copyCollection_doesPreservePermissions_whenDestCollectionExists() throws XMLDBException {
+ Collection test = DatabaseManager.getCollection(baseUri + "/db/securityTest3", "test1", "test1");
+ CollectionManagementServiceImpl cms = (CollectionManagementServiceImpl) test.getService("CollectionManagementService", "1.0");
+
+ //create collection owned by "test1", and group "users" in /db/securityTest3
+ Collection source = cms.createCollection("source");
+
+ //pre-create the dest collection and grant access to all (0777)
+ Collection dest = cms.createCollection("copy-of-source");
+ UserManagementService ums = (UserManagementService)dest.getService("UserManagementService", "1.0");
+ ums.chmod(0777);
+
+ //as the 'test3' user copy the collection
+ test = DatabaseManager.getCollection(baseUri + "/db/securityTest3", "test3", "test3");
+ cms = (CollectionManagementServiceImpl) test.getService("CollectionManagementService", "1.0");
+ cms.copy("/db/securityTest3/source", "/db/securityTest3", "copy-of-source");
+
+ //re-get ums as 'test3' user
+ ums = (UserManagementService) test.getService("UserManagementService", "1.0");
+ final Permission permissions = ums.getPermissions(test.getChildCollection("copy-of-source"));
+
+ //collection should STILL be owned by test1:users, i.e. permissions were preserved from the test1 users collection /db/securityTest3/copy-of-source
+ assertEquals("test1", permissions.getOwner().getName());
+ assertEquals("users", permissions.getGroup().getName());
+ }
+
+ /**
+ * As the 'test1' user, creates the collection and resource:
+ *
+ * test1:users /db/securityTest3/source
+ * test1:users /db/securityTest3/source/source.xml
+ *
+ *
+ * As the 'test3' user, copy the collection:
+ *
+ * /db/securityTest3/source
+ * -> /db/securityTest3/copy-of-source
+ */
+ @Test
+ public void copyCollectionWithResource_doesNotPreservePermissions() throws XMLDBException {
+ Collection test = DatabaseManager.getCollection(baseUri + "/db/securityTest3", "test1", "test1");
+ CollectionManagementServiceImpl cms = (CollectionManagementServiceImpl) test.getService("CollectionManagementService", "1.0");
+
+ //create collection owned by "test1", and group "users" in /db/securityTest3
+ Collection source = cms.createCollection("source");
+
+ //create resource owned by "test1", and group "users" in /db/securityTest3/source
+ final Resource resSource = source.createResource("source.xml", XMLResource.RESOURCE_TYPE);
+ resSource.setContent("<test/>");
+ source.storeResource(resSource);
+
+ //as the 'test3' user copy the collection
+ test = DatabaseManager.getCollection(baseUri + "/db/securityTest3", "test3", "test3");
+ cms = (CollectionManagementServiceImpl) test.getService("CollectionManagementService", "1.0");
+ cms.copy("/db/securityTest3/source", "/db/securityTest3", "copy-of-source");
+
+
+ UserManagementService ums = (UserManagementService) test.getService("UserManagementService", "1.0");
+ final Collection copyOfSource = test.getChildCollection("copy-of-source");
+ Permission permissions = ums.getPermissions(copyOfSource);
+
+ //collection should be owned by test3:guest, i.e. permissions were not preserved from the test1 users doc /db/securityTest3/source
+ assertEquals("test3", permissions.getOwner().getName());
+ assertEquals("guest", permissions.getGroup().getName());
+
+ ums = (UserManagementService) copyOfSource.getService("UserManagementService", "1.0");
+ final Resource resCopyOfSource = copyOfSource.getResource("source.xml");
+ permissions = ums.getPermissions(resCopyOfSource);
+
+ //resource in collection should be owned by test3:guest, i.e. permissions were not preserved from the test1 users doc /db/securityTest3/source.xml
+ assertEquals("test3", permissions.getOwner().getName());
+ assertEquals("guest", permissions.getGroup().getName());
+ }
+
+
+ /**
+ * As the 'test1' user, creates the collection and resource:
+ *
+ * test1:users /db/securityTest3/source
+ * test1:users /db/securityTest3/source/source1.xml
+ * test1:users /db/securityTest3/source/source2.xml
+ * test1:users /db/securityTest3/source/sub
+ * test1:users /db/securityTest3/source/sub/sub1.xml
+ *
+ *
+ * As the 'test3' user, copy the collection:
+ *
+ * /db/securityTest3/source
+ * -> /db/securityTest3/copy-of-source
+ */
+ @Test
+ public void copyCollectionWithResources_withSubCollectionWithResource_doesNotPreservePermissions() throws XMLDBException {
+ Collection test = DatabaseManager.getCollection(baseUri + "/db/securityTest3", "test1", "test1");
+ CollectionManagementServiceImpl cms = (CollectionManagementServiceImpl) test.getService("CollectionManagementService", "1.0");
+
+ //create collection owned by "test1", and group "users" in /db/securityTest3
+ Collection source = cms.createCollection("source");
+
+ //create resource owned by "test1", and group "users" in /db/securityTest3/source
+ Resource resSource = source.createResource("source1.xml", XMLResource.RESOURCE_TYPE);
+ resSource.setContent("<test/>");
+ source.storeResource(resSource);
+
+ resSource = source.createResource("source2.xml", XMLResource.RESOURCE_TYPE);
+ resSource.setContent("<test/>");