找到专用应用程序文件夹的位置

如果这个标题名称错误,我很抱歉,我想不出更好的方式来表达它,所以欢迎编辑。

我见过的大多数需要硬盘驱动器文件存储的应用程序根据操作系统在适当的位置创建一个文件夹。 在Windows上这些文件夹位于\ Users \ [current user] \ AppData \ [etc],在Mac上这些文件夹位于/ Users / [current user] / Library / Application Support / [etc],Ubuntu有类似的东西我现在想不到。

我想知道,这些文件路径在不同用户的不同操作系统中是如何一致的,至少在java中是否有一种简单的方法可以实现这一点?

谢谢。

应该有,但没有。 我甚至提交了一个关于它的bug / RFE,但据我所知,它从未被接受过。 这是我使用的:

public class ApplicationDirectories { private static final Logger logger = Logger.getLogger(ApplicationDirectories.class.getName()); private static final Path config; private static final Path data; private static final Path cache; static { String os = System.getProperty("os.name"); String home = System.getProperty("user.home"); if (os.contains("Mac")) { config = Paths.get(home, "Library", "Application Support"); data = config; cache = config; } else if (os.contains("Windows")) { String version = System.getProperty("os.version"); if (version.startsWith("5.")) { config = getFromEnv("APPDATA", false, Paths.get(home, "Application Data")); data = config; cache = Paths.get(home, "Local Settings", "Application Data"); } else { config = getFromEnv("APPDATA", false, Paths.get(home, "AppData", "Roaming")); data = config; cache = getFromEnv("LOCALAPPDATA", false, Paths.get(home, "AppData", "Local")); } } else { config = getFromEnv("XDG_CONFIG_HOME", true, Paths.get(home, ".config")); data = getFromEnv("XDG_DATA_HOME", true, Paths.get(home, ".local", "share")); cache = getFromEnv("XDG_CACHE_HOME", true, Paths.get(home, ".cache")); } } /** Prevents instantiation. */ private ApplicationDirectories() { } /** * Retrieves a path from an environment variable, substituting a default * if the value is absent or invalid. * * @param envVar name of environment variable to read * @param mustBeAbsolute whether enviroment variable's value should be * considered invalid if it's not an absolute path * @param defaultPath default to use if environment variable is absent * or invalid * * @return environment variable's value as a {@code Path}, * or {@code defaultPath} */ private static Path getFromEnv(String envVar, boolean mustBeAbsolute, Path defaultPath) { Path dir; String envDir = System.getenv(envVar); if (envDir == null || envDir.isEmpty()) { dir = defaultPath; logger.log(Level.CONFIG, envVar + " not defined in environment" + ", falling back on \"{0}\"", dir); } else { dir = Paths.get(envDir); if (mustBeAbsolute && !dir.isAbsolute()) { dir = defaultPath; logger.log(Level.CONFIG, envVar + " is not an absolute path" + ", falling back on \"{0}\"", dir); } } return dir; } /** * Returns directory where the native system expects an application * to store configuration files for the current user. No attempt is made * to create the directory, and no checks are done to see if it exists. * * @param appName name of application */ public static Path configDir(String appName) { return config.resolve(appName); } /** * Returns directory where the native system expects an application * to store implicit data files for the current user. No attempt is made * to create the directory, and no checks are done to see if it exists. * * @param appName name of application */ public static Path dataDir(String appName) { return data.resolve(appName); } /** * Returns directory where the native system expects an application * to store cached data for the current user. No attempt is made * to create the directory, and no checks are done to see if it exists. * * @param appName name of application */ public static Path cacheDir(String appName) { return cache.resolve(appName); } } 

一些说明:

我不确定旧Windows版本的代码是否必要,因为Java 8不能在Windows XP上运行。

XDG目录规范说“在这些环境变量中设置的所有路径必须是绝对的。 如果某个实现在任何这些变量中遇到相对路径,它应该认为该路径无效并忽略它。“

可以使用该方法找到该目录

 static String defaultDirectory() { String os = System.getProperty("os.name").toLowerCase(); if (OS.contains("win")) return System.getenv("APPDATA"); else if (OS.contains("mac")) return System.getProperty("user.home") + "/Library/Application Support"; else if (OS.contains("nux")) return System.getProperty("user.home"); else return System.getProperty("user.dir"); } 

值得注意的是,在Linux上,任何此类文件夹都应该通过以其名称开头来隐藏.

(在这篇文章中找到用户CodeBunny和Denis Tulskiy的答案)