我的 PC 在 Windows7 64 位下运行,我有一个实用程序(.exe,非常旧的 [~WinXP 时代],没有可用的资源),我想从部署到 Jetty 中的 Java 代码调用它。 如果我从控制台启动实用程序,我不会收到任何错误。如果我通过简单的 java 包装器启动实用程序:
import java.util.*;
import java.io.*;
public class Wrapper {
public static void main(String[] args) throws IOException {
System.out.println(System.getProperty("java.version"));
Runtime.getRuntime().exec("util.exe -opt1 -opt2");
}
}
我也没有收到任何错误。 但是如果我从 WAR I 中调用此代码(比 Runtime.getRuntime().exec("util.exe") 复杂一点,因为我需要计算二进制文件的绝对路径)使用以下消息获取 IOException:
CreateProcess error=216, This version of %1 is not compatible with the version of Windows you're running. Check your computer's system information to see whether you need a x86 (32-bit) or x64 (64-bit) version of the program, and then contact the software publisher
我尝试使用 -d32 选项启动 jetty ,尝试将不同版本的 java(JRE/JDK、6/7 和 32/64 位)放入 JAVA_HOME 和 PATH 中 — 但没有成功。
有人遇到过类似的问题吗?有可能解决吗?
[更新] 我附上了一些服务器代码。 CommandLine 和 FileUtils 是 Apache Commons 的一部分。 ApplicationContext 与 Spring Framework 相关。
public class ImageLoader implements ApplicationContextAware {
private final static String UTIL_EXECUTABLE = "util.exe";
private final static String TEMP_FILE_PREFIX = "tmpFilePrefix";
private ApplicationContext applicationContext;
private File binaryPath;
@PostConstruct
public void init() throws Exception {
if (applicationContext instanceof WebApplicationContext) {
Resource binaryRoot = applicationContext.getResource(
"WEB-INF/classes/executable");
this.binaryPath = binaryRoot.getFile();
}
}
@Override
public void setApplicationContext(ApplicationContext applicationContext) throws BeansException {
this.applicationContext = applicationContext;
}
/**
* Download db image from device.
*/
public byte[] downloadImage(Device device) throws LoaderException {
try {
File file = downloadWindows(device);
return FileUtils.readFileToByteArray(file);
} catch (Exception ex) {
throw new LoaderException("Error downloading file: " + ex.getMessage(), ex);
}
}
private File downloadWindows(final Device device) throws Exception {
File tmpFile = File.createTempFile(TEMP_FILE_PREFIX, null);
CommandLine command = generateCommand(ActionType.download, tmpFile, device.getTargetIP(), "user", "pass");
Runtime.getRuntime().exec(command.toString());
return tmpFile;
}
protected CommandLine generateCommand(ActionType actionType, File file, String targetIP, String userName, String userPassword) throws IOException {
String bin = this.binaryPath.getPath() + "\\" + UTIL_EXECUTABLE;
// safe to use \\ because code only runs if WAR deployed under Windows
CommandLine commandLine = new CommandLine(bin.replace("\\", "\\\\"));
commandLine.addArgument(actionType.name());
commandLine.addArgument(file.getAbsolutePath().replace("\\", "\\\\"));
commandLine.addArgument(targetIP);
commandLine.addArgument(userName);
commandLine.addArgument(userPassword);
return commandLine;
}
}
enum ActionType {
download,
upload
}
最佳答案
真为我和我的疏忽感到羞耻。问题实际上是在“其他地方”。 WAR 由 maven 构建,可执行文件的处理方式与任何其他资源一样,因此校验和与原始文件不同。我从过滤中排除了 exe 文件(在 pom.xml 中),它开始正常工作。
关于java - 通过 Runtime.exec 从 Web Archive 中的 Java 代码运行命令(部署在 Jetty 中的 WAR),我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/22786847/