如何在Java中以编程方式确定操作系统?

我想确定我的Java程序以编程方式运行的主机的操作系统(例如:我希望能够根据我是在Windows还是Unix平台上加载不同的属性)。100%可靠的最安全的方法是什么?

446400 次浏览

你可以使用:

System.getProperty("os.name")

附注:你可能会发现这段代码很有用:

class ShowProperties {
public static void main(String[] args) {
System.getProperties().list(System.out);
}
}

它所做的就是打印出Java实现提供的所有属性。它将使您了解通过属性可以了解Java环境的哪些信息。: -)

2008年10月:

我建议将它缓存到一个静态变量中:

public static final class OsUtils
{
private static String OS = null;
public static String getOsName()
{
if(OS == null) { OS = System.getProperty("os.name"); }
return OS;
}
public static boolean isWindows()
{
return getOsName().startsWith("Windows");
}


public static boolean isUnix() // and so on
}

这样,每次请求o时,在应用程序的生命周期内只获取一次属性。


2016年2月:7年多后:

Windows 10有一个错误(在最初的答案时不存在) 看到“# EYZ0”< / p >

如果你对一个开源项目是如何做这些事情感兴趣,你可以看看Terracotta类(Os.java)在这里处理这些垃圾:

你可以在这里看到类似的类来处理JVM版本(Vm.java和VmVersion.java):

我发现来自Swingx的OS Utils可以胜任这项工作。

如其他答案所示,系统。getProperty提供原始数据。然而,Apache Commons Lang组件提供了一个具有SystemUtils.IS_OS_WINDOWS这样方便属性的java.lang.System的包装器,很像前面提到的Swingx OS util。

String osName = System.getProperty("os.name");
System.out.println("Operating system " + osName);

你想要实现的一个小例子可能是一个类似下面的class:

import java.util.Locale;


public class OperatingSystem
{
private static String OS = System.getProperty("os.name", "unknown").toLowerCase(Locale.ROOT);


public static boolean isWindows()
{
return OS.contains("win");
}


public static boolean isMac()
{
return OS.contains("mac");
}


public static boolean isUnix()
{
return OS.contains("nux");
}
}

这个特殊的实现非常可靠,应该是普遍适用的。只需复制并粘贴到您的class选择。

上面答案中的一些链接似乎被打破了。我在下面的代码中添加了指向当前源代码的指针,并提供了一种方法来处理以enum作为答案的检查,以便在计算结果时使用switch语句:

OsCheck.OSType ostype=OsCheck.getOperatingSystemType();
switch (ostype) {
case Windows: break;
case MacOS: break;
case Linux: break;
case Other: break;
}

helper类是:

/**
* helper class to check the operating system this Java VM runs in
*
* please keep the notes below as a pseudo-license
*
* http://stackoverflow.com/questions/228477/how-do-i-programmatically-determine-operating-system-in-java
* compare to http://svn.terracotta.org/svn/tc/dso/tags/2.6.4/code/base/common/src/com/tc/util/runtime/Os.java
* http://www.docjar.com/html/api/org/apache/commons/lang/SystemUtils.java.html
*/
import java.util.Locale;
public static final class OsCheck {
/**
* types of Operating Systems
*/
public enum OSType {
Windows, MacOS, Linux, Other
};


// cached result of OS detection
protected static OSType detectedOS;


/**
* detect the operating system from the os.name System property and cache
* the result
*
* @returns - the operating system detected
*/
public static OSType getOperatingSystemType() {
if (detectedOS == null) {
String OS = System.getProperty("os.name", "generic").toLowerCase(Locale.ENGLISH);
if ((OS.indexOf("mac") >= 0) || (OS.indexOf("darwin") >= 0)) {
detectedOS = OSType.MacOS;
} else if (OS.indexOf("win") >= 0) {
detectedOS = OSType.Windows;
} else if (OS.indexOf("nux") >= 0) {
detectedOS = OSType.Linux;
} else {
detectedOS = OSType.Other;
}
}
return detectedOS;
}
}

我喜欢沃尔夫冈的回答,只是因为我相信这样的事情应该是consts……

所以我把它重新措辞了一下,并想分享一下:)

/**
* types of Operating Systems
*
* please keep the note below as a pseudo-license
*
* helper class to check the operating system this Java VM runs in
* http://stackoverflow.com/questions/228477/how-do-i-programmatically-determine-operating-system-in-java
* compare to http://svn.terracotta.org/svn/tc/dso/tags/2.6.4/code/base/common/src/com/tc/util/runtime/Os.java
* http://www.docjar.com/html/api/org/apache/commons/lang/SystemUtils.java.html
*/
public enum OSType {
MacOS("mac", "darwin"),
Windows("win"),
Linux("nux"),
Other("generic");


private static OSType detectedOS;


private final String[] keys;


private OSType(String... keys) {
this.keys = keys;
}


private boolean match(String osKey) {
for (int i = 0; i < keys.length; i++) {
if (osKey.indexOf(keys[i]) != -1)
return true;
}
return false;
}


public static OSType getOS_Type() {
if (detectedOS == null)
detectedOS = getOperatingSystemType(System.getProperty("os.name", Other.keys[0]).toLowerCase());
return detectedOS;
}


private static OSType getOperatingSystemType(String osKey) {
for (OSType osType : values()) {
if (osType.match(osKey))
return osType;
}
return Other;
}
}

试试这个,简单易行

System.getProperty("os.name");
System.getProperty("os.version");
System.getProperty("os.arch");

此代码用于显示有关系统操作系统类型、名称、java信息等的所有信息。

public static void main(String[] args) {
// TODO Auto-generated method stub
Properties pro = System.getProperties();
for(Object obj : pro.keySet()){
System.out.println(" System  "+(String)obj+"     :  "+System.getProperty((String)obj));
}
}

下面的代码显示了你可以从System API得到的值,这些都可以通过这个API得到。

public class App {
public static void main( String[] args ) {
//Operating system name
System.out.println(System.getProperty("os.name"));


//Operating system version
System.out.println(System.getProperty("os.version"));


//Path separator character used in java.class.path
System.out.println(System.getProperty("path.separator"));


//User working directory
System.out.println(System.getProperty("user.dir"));


//User home directory
System.out.println(System.getProperty("user.home"));


//User account name
System.out.println(System.getProperty("user.name"));


//Operating system architecture
System.out.println(System.getProperty("os.arch"));


//Sequence used by operating system to separate lines in text files
System.out.println(System.getProperty("line.separator"));


System.out.println(System.getProperty("java.version")); //JRE version number


System.out.println(System.getProperty("java.vendor.url")); //JRE vendor URL


System.out.println(System.getProperty("java.vendor")); //JRE vendor name


System.out.println(System.getProperty("java.home")); //Installation directory for Java Runtime Environment (JRE)


System.out.println(System.getProperty("java.class.path"));


System.out.println(System.getProperty("file.separator"));
}
}

答案:-

Windows 7
6.1
;
C:\Users\user\Documents\workspace-eclipse\JavaExample
C:\Users\user
user
amd64




1.7.0_71
http://java.oracle.com/
Oracle Corporation
C:\Program Files\Java\jre7
C:\Users\user\Documents\workspace-Eclipse\JavaExample\target\classes
\

博士TL;

访问操作系统使用:System.getProperty("os.name")


但是等等! !

为什么不创建一个实用工具类,使其可重用!而且在多次通话中可能会更快。# EYZ0

为这样的实用函数创建一个Util类。然后为每种操作系统类型创建公共枚举。

public class Util {
public enum OS {
WINDOWS, LINUX, MAC, SOLARIS
};// Operating systems.


private static OS os = null;


public static OS getOS() {
if (os == null) {
String operSys = System.getProperty("os.name").toLowerCase();
if (operSys.contains("win")) {
os = OS.WINDOWS;
} else if (operSys.contains("nix") || operSys.contains("nux")
|| operSys.contains("aix")) {
os = OS.LINUX;
} else if (operSys.contains("mac")) {
os = OS.MAC;
} else if (operSys.contains("sunos")) {
os = OS.SOLARIS;
}
}
return os;
}
}

现在,您可以轻松地从任何类中调用类,如下所示由于我们将os变量声明为静态,它只会花费一次时间来识别系统类型,然后它可以一直使用到应用程序停止。)

            switch (Util.getOS()) {
case WINDOWS:
//do windows stuff
break;
case LINUX:

就是这样!

你可以使用sun.awt.OSInfo#getOSType()方法

以下JavaFX类有静态方法来确定当前的操作系统(isWindows(),isLinux()…):

  • com.sun.javafx.PlatformUtil
  • com.sun.media.jfxmediaimpl.HostUtils
  • com.sun.javafx.util.Utils

例子:

if (PlatformUtil.isWindows()){
...
}

我认为下面的内容可以用更少的字里行间覆盖更广的范围

import org.apache.commons.exec.OS;


if (OS.isFamilyWindows()){
//load some property
}
else if (OS.isFamilyUnix()){
//load some other property
}

更多细节:https://commons.apache.org/proper/commons-exec/apidocs/org/apache/commons/exec/OS.html

在com.sun.jna.Platform类中,您可以找到有用的静态方法,例如

Platform.isWindows();
Platform.is64Bit();
Platform.isIntel();
Platform.isARM();

还有更多。

如果使用Maven,只需添加依赖项

<dependency>
<groupId>net.java.dev.jna</groupId>
<artifactId>jna</artifactId>
<version>5.2.0</version>
</dependency>

否则,只需找到jna库jar文件(例如jna-5.2.0.jar)并将其添加到类路径。

使用如下所示的com.sun.javafx.util.Utils即可。

if ( Utils.isWindows()){
// LOGIC HERE
}

# EYZ0

boolean isWindows = OSInfo.getOSType().equals(OSInfo.OSType.WINDOWS);
if (isWindows){
// YOUR LOGIC HERE
}

如果您正在安全敏感的环境中工作,那么请通读本文。

请不要相信通过System#getProperty(String)子例程获得的属性!实际上,包括os.archos.nameos.version在内的几乎每个属性都不是您所期望的只读属性——相反,它们实际上恰恰相反。

首先,任何具有调用System#setProperty(String, String)子例程的足够权限的代码都可以随意修改返回的文字。然而,这并不一定是这里的主要问题,因为它可以通过使用所谓的SecurityManager来解决,正如在在这里上更详细地描述的那样。

实际的问题是,任何用户都可以在运行JAR时编辑这些属性(通过-Dos.name=-Dos.arch=等)。避免篡改应用程序参数的一种可能方法是查询RuntimeMXBean,如在这里所示。下面的代码片段应该提供一些关于如何实现这一点的见解。

RuntimeMXBean runtimeMxBean = ManagementFactory.getRuntimeMXBean();
List<String> arguments = runtimeMxBean.getInputArguments();


for (String argument : arguments) {
if (argument.startsWith("-Dos.name") {
// System.getProperty("os.name") altered
} else if (argument.startsWith("-Dos.arch") {
// System.getProperty("os.arch") altered
}
}

下面是一些简短、简洁(并且热切地计算过)的顶级答案:

switch(OSType.DETECTED){
...
}

helper enum:

public enum OSType {
Windows, MacOS, Linux, Other;
public static final  OSType DETECTED;
static{
String OS = System.getProperty("os.name", "generic").toLowerCase(Locale.ENGLISH);
if ((OS.contains("mac")) || (OS.contains("darwin"))) {
DETECTED = OSType.MacOS;
} else if (OS.contains("win")) {
DETECTED = OSType.Windows;
} else if (OS.contains("nux")) {
DETECTED = OSType.Linux;
} else {
DETECTED = OSType.Other;
}
}
}

由于谷歌点"kotlin os名称"到这个页面,这里是@Memin的回答的Kotlin版本:

private var _osType: OsTypes? = null
val osType: OsTypes
get() {
if (_osType == null) {
_osType = with(System.getProperty("os.name").lowercase(Locale.getDefault())) {
if (contains("win"))
OsTypes.WINDOWS
else if (listOf("nix", "nux", "aix").any { contains(it) })
OsTypes.LINUX
else if (contains("mac"))
OsTypes.MAC
else if (contains("sunos"))
OsTypes.SOLARIS
else
OsTypes.OTHER
}
}
return _osType!!
}


enum class OsTypes {
WINDOWS, LINUX, MAC, SOLARIS, OTHER
}

获取操作系统名称,只需使用:

Platform.getOS()

假设你想看看平台是否是linux:

if (Platform.getOS().equals(Platform.OS_LINUX)) {
}

类似地,Platform类为其他操作系统名称定义了常量。平台类是org.eclipse.core.runtime包的一部分。