From 33c9a8afabe51a2fd433875149d4b96cce66e306 Mon Sep 17 00:00:00 2001 From: srosse <none@none> Date: Mon, 2 Mar 2015 21:52:52 +0100 Subject: [PATCH] OO-1455: check the security callback with the recursive method of container --- .../webdav/manager/VFSResourceRoot.java | 6 +- .../services/webdav/WebDAVCommandsTest.java | 110 +++++++++++++++++- .../services/webdav/WebDAVConnection.java | 11 +- .../core/commons/services/webdav/mkdirs.zip | Bin 0 -> 12423 bytes 4 files changed, 122 insertions(+), 5 deletions(-) create mode 100644 src/test/java/org/olat/core/commons/services/webdav/mkdirs.zip diff --git a/src/main/java/org/olat/core/commons/services/webdav/manager/VFSResourceRoot.java b/src/main/java/org/olat/core/commons/services/webdav/manager/VFSResourceRoot.java index 0e47b713dea..aa1c835199b 100644 --- a/src/main/java/org/olat/core/commons/services/webdav/manager/VFSResourceRoot.java +++ b/src/main/java/org/olat/core/commons/services/webdav/manager/VFSResourceRoot.java @@ -159,8 +159,10 @@ public class VFSResourceRoot implements WebResourceRoot { } else if (parentItem instanceof VFSContainer) { String name = path.substring(lastSlash + 1); VFSContainer folder = (VFSContainer)parentItem; - VFSContainer dir = folder.createChildContainer(name); - return dir != null && dir.exists(); + if(folder.canWrite() == VFSConstants.YES) { + VFSContainer dir = folder.createChildContainer(name); + return dir != null && dir.exists(); + } } return false; } diff --git a/src/test/java/org/olat/core/commons/services/webdav/WebDAVCommandsTest.java b/src/test/java/org/olat/core/commons/services/webdav/WebDAVCommandsTest.java index 9a74b0c2f25..15fb3804ecc 100644 --- a/src/test/java/org/olat/core/commons/services/webdav/WebDAVCommandsTest.java +++ b/src/test/java/org/olat/core/commons/services/webdav/WebDAVCommandsTest.java @@ -51,6 +51,8 @@ import org.olat.core.commons.modules.bc.vfs.OlatRootFolderImpl; import org.olat.core.commons.persistence.DB; import org.olat.core.id.Identity; import org.olat.core.id.Roles; +import org.olat.core.logging.OLog; +import org.olat.core.logging.Tracing; import org.olat.core.util.FileUtils; import org.olat.core.util.vfs.VFSContainer; import org.olat.core.util.vfs.VFSItem; @@ -75,6 +77,8 @@ import org.springframework.beans.factory.annotation.Autowired; */ public class WebDAVCommandsTest extends WebDAVTestCase { + private static final OLog log = Tracing.createLoggerFor(WebDAVCommandsTest.class); + @Autowired private DB dbInstance; @Autowired @@ -520,7 +524,7 @@ public class WebDAVCommandsTest extends WebDAVTestCase { //author check file URI textUri = conn.getBaseURI().path("webdav").path("home").path("public").path("test.txt").build(); String textPropfind = conn.propfind(textUri, 0); - System.out.println(textPropfind); + log.info(textPropfind); //author lock the file String lockToken = conn.lock(textUri, UUID.randomUUID().toString()); @@ -664,6 +668,101 @@ public class WebDAVCommandsTest extends WebDAVTestCase { conn.close(); } + /** + * Check that different methods doesn't create directory + * + * @throws IOException + * @throws URISyntaxException + */ + @Test + public void coursePermission_participantDirectory() + throws IOException, URISyntaxException { + webDAVModule.setEnableLearnersBookmarksCourse(true); + webDAVModule.setEnableLearnersParticipatingCourses(true); + + //create a user + Identity auth = JunitTestHelper.createAndPersistIdentityAsAuthor("webdav-4-" + UUID.randomUUID().toString()); + Identity participant = JunitTestHelper.createAndPersistIdentityAsRndUser("webdav-5"); + RepositoryEntry courseEntry = deployMkdirsCourse(auth); + repositoryEntryRelationDao.addRole(participant, courseEntry, GroupRoles.participant.name()); + dbInstance.commitAndCloseSession(); + + //put a reference file there + ICourse course = CourseFactory.loadCourse(courseEntry.getOlatResource()); + VFSContainer elements = (VFSContainer)course.getCourseFolderContainer().resolve("_courseelementdata"); + Assert.assertNotNull(elements); + VFSContainer directory = (VFSContainer)elements.resolve("Directory"); + VFSContainer level_1_Container = directory.createChildContainer("DT_01"); + + VFSLeaf readonlyLeaf = level_1_Container.createChildLeaf("readonly.txt"); + InputStream in = WebDAVCommandsTest.class.getResourceAsStream("text.txt"); + OutputStream out = readonlyLeaf.getOutputStream(false); + FileUtils.copy(in, out); + + //check + VFSItem readonlyLeafBis = level_1_Container.resolve("readonly.txt"); + Assert.assertNotNull(readonlyLeafBis); + + + //participant try to put a file + WebDAVConnection conn = new WebDAVConnection(); + conn.setCredentials(participant.getName(), "A6B7C8"); + URI courseUri = conn.getBaseURI().path("webdav").path("coursefolders").path("other").path("Mkdirs").build(); + + + //MKCOL in the folder at the second level + URI level2Uri = UriBuilder.fromUri(courseUri).path("_courseelementdata") + .path("Directory").path("DT_01").path("DT_11").build(); + int mkcol2Code = conn.mkcol(level2Uri); + Assert.assertEquals(409, mkcol2Code); + //check + VFSItem level2Mkcol = level_1_Container.resolve("DT_11"); + Assert.assertNull(level2Mkcol); + + + //MKCOL in the folder at the first level + URI level1Uri = UriBuilder.fromUri(courseUri).path("_courseelementdata") + .path("Directory").path("DT_02").build(); + int mkcol1Code = conn.mkcol(level1Uri); + Assert.assertEquals(409, mkcol1Code); + VFSItem level1Mkcol = directory.resolve("DT_02"); + Assert.assertNull(level1Mkcol); + + + //PROPFIND in second level + int propfind2Code = conn.propfindTry(level2Uri, 1); + Assert.assertEquals(404, propfind2Code); + //check + VFSItem level2Propfind = level_1_Container.resolve("DT_11"); + Assert.assertNull(level2Propfind); + + + //PROPFIND in first level + int propfind1Code = conn.propfindTry(level2Uri, 1); + Assert.assertEquals(404, propfind1Code); + //check + VFSItem level1Propfind = level_1_Container.resolve("DT_02"); + Assert.assertNull(level1Propfind); + + + //LOCK in the second level + int lock2Code = conn.lockTry(level2Uri, UUID.randomUUID().toString()); + Assert.assertEquals(403, lock2Code); + //check + VFSItem level2Lock = level_1_Container.resolve("DT_11"); + Assert.assertNull(level2Lock); + + + //LOCK in the first level + int lock1Code = conn.lockTry(level2Uri, UUID.randomUUID().toString()); + Assert.assertEquals(403, lock1Code); + //check + VFSItem level1Lock = level_1_Container.resolve("DT_02"); + Assert.assertNull(level1Lock); + + IOUtils.closeQuietly(conn); + } + @Test public void customizingFolder() throws IOException, URISyntaxException { @@ -679,7 +778,8 @@ public class WebDAVCommandsTest extends WebDAVTestCase { Assert.assertTrue(customizingXml.contains("<D:href>/webdav/customizing/</D:href>")); //PUT in the folder - URI textUri = conn.getBaseURI().path("webdav").path("customizing").path("infos.txt").build(); + String randomFilename = "infos" + UUID.randomUUID() + ".txt"; + URI textUri = conn.getBaseURI().path("webdav").path("customizing").path(randomFilename).build(); HttpPut put = conn.createPut(textUri); InputStream dataStream = WebDAVCommandsTest.class.getResourceAsStream("text.txt"); InputStreamEntity entity = new InputStreamEntity(dataStream, -1); @@ -727,6 +827,12 @@ public class WebDAVCommandsTest extends WebDAVTestCase { return container.resolve(filename); } + private RepositoryEntry deployMkdirsCourse(Identity author) + throws URISyntaxException { + URL courseWithForumsUrl = WebDAVCommandsTest.class.getResource("mkdirs.zip"); + return deployTestCourse(author, null, courseWithForumsUrl); + } + private RepositoryEntry deployTestCourse(Identity author, Identity coAuthor) throws URISyntaxException { URL courseWithForumsUrl = CoursePublishTest.class.getResource("myCourseWS.zip"); diff --git a/src/test/java/org/olat/core/commons/services/webdav/WebDAVConnection.java b/src/test/java/org/olat/core/commons/services/webdav/WebDAVConnection.java index 39d00bef97a..ec406754edb 100644 --- a/src/test/java/org/olat/core/commons/services/webdav/WebDAVConnection.java +++ b/src/test/java/org/olat/core/commons/services/webdav/WebDAVConnection.java @@ -119,8 +119,17 @@ public class WebDAVConnection implements Closeable { HttpPropFind propfind = new HttpPropFind(uri); propfind.addHeader("Depth", Integer.toString(depth)); HttpResponse response = execute(propfind); + String text = EntityUtils.toString(response.getEntity()); Assert.assertEquals(207, response.getStatusLine().getStatusCode()); - return EntityUtils.toString(response.getEntity()); + return text; + } + + public int propfindTry(URI uri, int depth) throws IOException, URISyntaxException { + HttpPropFind propfind = new HttpPropFind(uri); + propfind.addHeader("Depth", Integer.toString(depth)); + HttpResponse response = execute(propfind); + EntityUtils.consumeQuietly(response.getEntity()); + return response.getStatusLine().getStatusCode(); } public int mkcol(URI uri) throws IOException, URISyntaxException { diff --git a/src/test/java/org/olat/core/commons/services/webdav/mkdirs.zip b/src/test/java/org/olat/core/commons/services/webdav/mkdirs.zip new file mode 100644 index 0000000000000000000000000000000000000000..d2e11b74d9cbbe1d0ae4a0830ab6bd4da43e3457 GIT binary patch literal 12423 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 literal 0 HcmV?d00001 -- GitLab