开发者

how to set Hidden proprerty of a file

I'm trying to create a static method that let me hide a file. I've found some possible way to do that and开发者_StackOverflow中文版 I wrote this:

public static void hide(File src) throws InterruptedException, IOException {

    if(System.getProperty("os.name").contains("Windows"))
    {
        Process p = Runtime.getRuntime().exec("attrib +h " + src.getPath());
        p.waitFor();
    }
    else
    {
        src.renameTo(new File(src.getParent()+File.separator+"."+src.getName()));
    }
}

Unfortunatley this isn't working in windows and neither on Ubuntu... In Oracle's tuorials I've found this way

Path file = ...;

Files.setAttribute(file, "dos:hidden", true);

but I don't know how to use it because my JDK doesn't have the class "Path". Can anyone help me with a method that can work in unix OS and Windows?


The Path class was introduced in Java 7.

Before Java 7 there was no built-in way to access properties like this, so you'll have to do something similar to what you're trying (and on Unix-y OS there is no "hidden property", but all files that start with a . are hidden by default).

Regarding your exec() call there's a great (if a bit old) article that lists all the stuff that can go wrong and how to fix it (it's quite an involved process, unfortunately).

And a minor note: new File(src.getParent()+File.separator+"."+src.getName()) can be replaced by new File(src.getParent(), "." + src.getName()), which would be a bit cleaner.


If a file as not parent, getParent() will return null. Perhaps what you wanted for unix was

src.renameTo(new File(src.getParent(), '.'+src.getName()));

Path is available in Java 7.


you won't be able to achieve this with standard JDK code. The File class offers an isHidden method, however, it states clearly that the concept of hidden is file system dependent:

Tests whether the file named by this abstract pathname is a hidden file. The exact definition of hidden is system-dependent. On UNIX systems, a file is considered to be hidden if its name begins with a period character ('.'). On Microsoft Windows systems, a file is considered to be hidden if it has been marked as such in the filesystem.

As such you need to write platform specific code (JNI?) to hide a file.


Operating system detection code:

public class OperatingSystemUtilities
{
    private static String operatingSystem = null;

    private static String getOperatingSystemName()
    {
        if (operatingSystem == null)
        {
            operatingSystem = System.getProperty("os.name");
        }

        return operatingSystem;
    }

    public static boolean isWindows()
    {
        String operatingSystemName = getOperatingSystemName();
        return operatingSystemName.startsWith("Windows");
    }

    public static boolean isMacOSX()
    {
        String operatingSystemName = getOperatingSystemName();
        return operatingSystemName.startsWith("Mac OS X");
    }

    public static boolean isUnix()
    {
        return !isWindows();
    }
}

Hiding the file code:

public static String hideFile(String filePath) throws IOException
{
    Path path = Paths.get(filePath);

    if (OperatingSystemUtilities.isWindows())
    {
        Files.setAttribute(path, "dos:hidden", Boolean.TRUE, LinkOption.NOFOLLOW_LINKS);
        return path.toString();
    } else if (OperatingSystemUtilities.isUnix())
    {
        String filename = path.getFileName().toString();

        if (filename.startsWith("."))
        {
            return path.toString();
        }

        // Keep trying to rename
        while (true)
        {
            Path parent = path.toAbsolutePath().getParent();
            Path newPath = Paths.get(parent + File.separator + "." + filename);

            // Modify the file name when it exists
            if (Files.exists(newPath))
            {
                int lastDotIndex = filename.lastIndexOf(".");

                if (lastDotIndex == -1)
                {
                    lastDotIndex = filename.length();
                }

                Random random = new Random();
                int randomNumber = random.nextInt();
                randomNumber = Math.abs(randomNumber);
                filename = filename.substring(0, lastDotIndex) + randomNumber + filename.substring(lastDotIndex, filename.length());

                continue;
            }

            Files.move(path, newPath);

            return newPath.toString();
        }
    }

    throw new IllegalStateException("Unsupported OS!");
}

Note that you have to pay attention to avoid a file name clash when renaming to hide the file on Unix. This is what the code implements despite it being unlikely.

0

上一篇:

下一篇:

精彩评论

暂无评论...
验证码 换一张
取 消

最新问答

问答排行榜