This is an automated email from the ASF dual-hosted git repository. lkishalmi pushed a commit to branch master in repository https://gitbox.apache.org/repos/asf/netbeans.git
The following commit(s) were added to refs/heads/master by this push: new b0d67bcd69 Made FileUtil to copy POSIX permissions b0d67bcd69 is described below commit b0d67bcd6925dc6efcf33058c6379873dd55aec2 Author: Laszlo Kishalmi <laszlo.kisha...@gmail.com> AuthorDate: Sun Sep 18 23:07:44 2022 -0700 Made FileUtil to copy POSIX permissions --- platform/openide.filesystems/apichanges.xml | 24 +++++++++ platform/openide.filesystems/manifest.mf | 2 +- .../src/org/openide/filesystems/FileObject.java | 3 +- .../src/org/openide/filesystems/FileUtil.java | 57 ++++++++++++++++++++-- .../src/org/openide/filesystems/FileUtilTest.java | 25 ++++++++++ 5 files changed, 104 insertions(+), 7 deletions(-) diff --git a/platform/openide.filesystems/apichanges.xml b/platform/openide.filesystems/apichanges.xml index c21da31428..eb98834fa5 100644 --- a/platform/openide.filesystems/apichanges.xml +++ b/platform/openide.filesystems/apichanges.xml @@ -25,6 +25,30 @@ <apidef name="filesystems">Filesystems API</apidef> </apidefs> <changes> + <change id="fileutil.copyposixperms"> + <api name="filesystems"/> + <summary>FileObject copy preserves source posix permissions.</summary> + <version major="9" minor="32"/> + <date day="12" month="1" year="2023"/> + <author login="lkishalmi"/> + <compatibility addition="yes" semantic="compatible"/> + <description> + <a href="@TOP@/org/openide/filesystems/FileUtil.html#copyFile-org.openide.filesystems.FileObject-org.openide.filesystems.FileObject-java.lang.String-java.lang.String-">FileUtil.copyFile(...)</a> now preserve ATTRIBUTES and POSIX permissions. + </description> + <class name="FileUtil" package="org.openide.filesystems"/> + </change> + <change id="fileutil.niofilepath"> + <api name="filesystems"/> + <summary>FileUtil can convert FileObject to/from java.nio.file.Path.</summary> + <version major="9" minor="32"/> + <date day="12" month="1" year="2023"/> + <author login="lkishalmi"/> + <compatibility addition="yes" semantic="compatible"/> + <description> + <a href="@TOP@/org/openide/filesystems/FileUtil.html#">FileUtil</a> has a <code>toPath(FileObject fo)</code> and <code>toFileObject(Path path)</code> utility methods. + </description> + <class name="FileUtil" package="org.openide.filesystems"/> + </change> <change id="fileutil.copyattr.trasnform"> <api name="filesystems"/> <summary>Allow to filter or transform attribute values during copying.</summary> diff --git a/platform/openide.filesystems/manifest.mf b/platform/openide.filesystems/manifest.mf index 14c80d034d..2016034220 100644 --- a/platform/openide.filesystems/manifest.mf +++ b/platform/openide.filesystems/manifest.mf @@ -2,6 +2,6 @@ Manifest-Version: 1.0 OpenIDE-Module: org.openide.filesystems OpenIDE-Module-Localizing-Bundle: org/openide/filesystems/Bundle.properties OpenIDE-Module-Layer: org/openide/filesystems/resources/layer.xml -OpenIDE-Module-Specification-Version: 9.31 +OpenIDE-Module-Specification-Version: 9.32 diff --git a/platform/openide.filesystems/src/org/openide/filesystems/FileObject.java b/platform/openide.filesystems/src/org/openide/filesystems/FileObject.java index 66bc740c23..7587619039 100644 --- a/platform/openide.filesystems/src/org/openide/filesystems/FileObject.java +++ b/platform/openide.filesystems/src/org/openide/filesystems/FileObject.java @@ -114,7 +114,8 @@ public abstract class FileObject extends Object implements Serializable, Lookup. /** Copies this file. This allows the filesystem to perform any additional * operation associated with the copy. But the default implementation is simple - * copy of the file and its attributes + * copy of the file and its attributes Since version 9.32, the file POSIX + * permissions are copied as well. * * @param target target folder to move this file to * @param name new basename of file diff --git a/platform/openide.filesystems/src/org/openide/filesystems/FileUtil.java b/platform/openide.filesystems/src/org/openide/filesystems/FileUtil.java index 8aa969d573..59c8524690 100644 --- a/platform/openide.filesystems/src/org/openide/filesystems/FileUtil.java +++ b/platform/openide.filesystems/src/org/openide/filesystems/FileUtil.java @@ -35,9 +35,11 @@ import java.net.URI; import java.net.URISyntaxException; import java.net.URL; import java.net.URLStreamHandler; +import java.nio.file.Files; import java.nio.file.InvalidPathException; import java.nio.file.Path; import java.nio.file.Paths; +import java.nio.file.attribute.PosixFilePermission; import java.util.ArrayList; import java.util.Collection; import java.util.Collections; @@ -538,7 +540,8 @@ public final class FileUtil extends Object { } /** Copies file to the selected folder. - * This implementation simply copies the file by stream content. + * This implementation simply copies the file by stream content. Since version + * 9.32, the file POSIX permissions are copied as well. * @param source source file object * @param destFolder destination folder * @param newName file name (without extension) of destination file @@ -567,6 +570,7 @@ public final class FileUtil extends Object { } copy(bufIn, bufOut); + copyPosixPerms(source, dest); copyAttributes(source, dest); } finally { if (bufIn != null) { @@ -584,6 +588,17 @@ public final class FileUtil extends Object { return dest; } + + static void copyPosixPerms(FileObject source, FileObject dest) throws IOException { + Path src = toPath(source); + Path dst = toPath(dest); + if ((src != null) && (dst != null)) { + try { + Set<PosixFilePermission> perms = Files.getPosixFilePermissions(src); + Files.setPosixFilePermissions(dst, perms); + } catch (UnsupportedOperationException ex) {} + } + } // // public methods @@ -605,7 +620,9 @@ public final class FileUtil extends Object { } /** Copies file to the selected folder. - * This implementation simply copies the file by stream content. + * This implementation simply copies the file by stream content. Since version + * 9.32, the file POSIX permissions are copied as well. + * * @param source source file object * @param destFolder destination folder * @param newName file name (without extension) of destination file @@ -620,7 +637,8 @@ public final class FileUtil extends Object { } /** Copies file to the selected folder. - * This implementation simply copies the file by stream content. + * This implementation simply copies the file by stream content. Since version + * 9.32, the file POSIX permissions are copied as well. * Uses the extension of the source file. * @param source source file object * @param destFolder destination folder @@ -832,10 +850,22 @@ public final class FileUtil extends Object { assert assertNormalized(retVal, BaseUtilities.isMac()); // #240180 return retVal; } + + /** Finds appropriate java.nio.file.Path to FileObject if possible. + * If not possible then null is returned. + * This is the inverse operation of {@link #toFileObject}. + * @param fo FileObject whose corresponding Path will be looked for + * @return java.nio.file.Path or null if no corresponding File exists. + * @since 9.32 + */ + public static Path toPath(FileObject fo) { + File f = toFile(fo); + return f != null ? f.toPath() : null; + } /** * Converts a disk file to a matching file object. - * This is the inverse operation of {@link #toFile}. + * This is the inverse operation of {@link #toFile(org.openide.filesystems.FileObject) }. * <p class="nonnormative"> * If you are running with {@code org.netbeans.modules.masterfs} enabled, * this method should never return null for a file which exists on disk. @@ -896,7 +926,24 @@ public final class FileUtil extends Object { } return retVal; } - + + /** + * Converts a Path to a FileObject if that is possible. It uses the + * {@link #toFileObject(java.io.File)} method with {@code path.toFile()}. + * if the conversion is not possible for some reason {@code null} is returned. + * + * @param path the {@link Path} to be converted + * @return the {@link FileObject} representing the {@code path} or {@code null} + * @since 9.32 + */ + public static FileObject toFileObject(Path path) { + try { + return toFileObject(path.toFile()); + } catch (UnsupportedOperationException ex) { + return null; + } + } + /** Finds appropriate FileObjects to java.io.File if possible. * If not possible then empty array is returned. More FileObjects may * correspond to one java.io.File that`s why array is returned. diff --git a/platform/openide.filesystems/test/unit/src/org/openide/filesystems/FileUtilTest.java b/platform/openide.filesystems/test/unit/src/org/openide/filesystems/FileUtilTest.java index 210b27f487..ff894afa57 100644 --- a/platform/openide.filesystems/test/unit/src/org/openide/filesystems/FileUtilTest.java +++ b/platform/openide.filesystems/test/unit/src/org/openide/filesystems/FileUtilTest.java @@ -24,18 +24,23 @@ import java.io.IOException; import java.lang.reflect.Method; import java.lang.reflect.Modifier; import java.net.URL; +import java.nio.file.Files; +import java.nio.file.attribute.PosixFilePermission; import java.util.ArrayList; import java.util.Arrays; import java.util.Collections; import java.util.HashMap; +import java.util.HashSet; import java.util.List; import java.util.Map; +import java.util.Set; import java.util.concurrent.atomic.AtomicInteger; import java.util.logging.Handler; import java.util.logging.Level; import java.util.logging.LogRecord; import java.util.logging.Logger; import junit.framework.Test; +import static org.junit.Assume.assumeFalse; import org.netbeans.junit.Log; import org.netbeans.junit.NbTestCase; import org.netbeans.junit.NbTestSuite; @@ -44,6 +49,7 @@ import org.openide.util.Exceptions; import org.openide.util.Lookup; import org.openide.util.RequestProcessor; import org.openide.util.BaseUtilities; +import org.openide.util.Utilities; import org.openide.util.test.MockLookup; /** @@ -704,6 +710,25 @@ public class FileUtilTest extends NbTestCase { assertTrue(result.toExternalForm().endsWith("/")); //NOI18N } + public void testCopyPosixPerms() throws Exception { + assumeFalse(Utilities.isWindows()); + + LocalFileSystem lfs = new LocalFileSystem(); + lfs.setRootDirectory(new File("/")); + FileObject workDir = lfs.findResource(getWorkDir().getAbsolutePath()); + clearWorkDir(); + + FileObject source = workDir.createData("original.file"); + Set<PosixFilePermission> perms = new HashSet<>(Files.getPosixFilePermissions(FileUtil.toPath(source))); + assertFalse(perms.contains(PosixFilePermission.OWNER_EXECUTE)); + perms.add(PosixFilePermission.OWNER_EXECUTE); + Files.setPosixFilePermissions(FileUtil.toPath(source), perms); + + FileObject dest = FileUtil.copyFile(source, workDir, "copied.file"); + perms = Files.getPosixFilePermissions(FileUtil.toPath(dest)); + assertTrue(perms.contains(PosixFilePermission.OWNER_EXECUTE)); + } + public void testCopyAttributes() throws Exception { FileObject testRoot = FileUtil.createMemoryFileSystem().getRoot(); FileObject aFile = testRoot.createData("a", "file"); --------------------------------------------------------------------- To unsubscribe, e-mail: commits-unsubscr...@netbeans.apache.org For additional commands, e-mail: commits-h...@netbeans.apache.org For further information about the NetBeans mailing lists, visit: https://cwiki.apache.org/confluence/display/NETBEANS/Mailing+lists