Java processbuilder 和使用环境变量
Java processbuilder and using environment variables
我想做的是运行一个进程,但是因为这个进程本身依赖环境变量,直接调用导致进程内部出错。对于那些想知道这是什么的人,这是 rake
工具。出于这个原因,我想也许最好使用 bash
并通过 bash
使用它会消除问题。然而,情况似乎并非如此。
这是我的代码:
public static void runPB(String directory) throws IOException {
ProcessBuilder processBuilder = new ProcessBuilder(
"/bin/bash");
processBuilder.directory(new File(directory));
Process process = processBuilder.start();
OutputStreamWriter osw = new OutputStreamWriter(process.getOutputStream());
osw.write("rake routes");
osw.close();
printStream(process.getErrorStream());
printStream(process.getInputStream());
}
public static void printStream(InputStream is) throws IOException {
InputStreamReader isr = new InputStreamReader(is);
BufferedReader br = new BufferedReader(isr);
String line;
while ((line = br.readLine()) != null) {
System.out.println(line);
}
}
我知道这是与环境相关的问题,因为这里描述了我遇到的错误 cannot load such file -- bundler/setup (LoadError)
我进一步检查了 processBuilder.environment()
returns 比输入 env
更少的环境变量。我继续更改 osw.write()
行并尝试 echo $GEM_HOME
那里,它不打印任何东西,如果我在我的操作系统上这样做 bash 然后我得到了路径,我也尝试了其他echo $SHELL
之类的常见事物,它在 Java 代码和 bash.
中打印 shell 位置
所以我的问题是:
1) 为什么我的操作系统的环境变量与 ProcessBuilder.environment()
方法不同?
2) Process
class 是否考虑使用 ProcessBuilder.environment()
给出的环境变量?如果是这样,那么我们如何从操作系统级别添加缺失的?
1) 您在 java 进程中看到的变量是从您启动 java 进程的进程继承而来的。 IE。如果您从 shell 启动它,它应该具有与 shell 相同的变量。在启动您的 Java 应用程序之前,您需要调查实际设置了哪些变量,以及为什么没有在该上下文中设置您期望的变量。
回答第 2 部分,是的,该过程将在 ProcessBuilder.environment()
中的环境中启动。您可以简单地向 ProcessBuilder.environment()
返回的地图添加内容,这将扩展运行时环境:
ProcessBuilder pb = new ProcessBuilder("foo");
pb.environment().put("MY_VAR", "foobar");
我想做的是运行一个进程,但是因为这个进程本身依赖环境变量,直接调用导致进程内部出错。对于那些想知道这是什么的人,这是 rake
工具。出于这个原因,我想也许最好使用 bash
并通过 bash
使用它会消除问题。然而,情况似乎并非如此。
这是我的代码:
public static void runPB(String directory) throws IOException {
ProcessBuilder processBuilder = new ProcessBuilder(
"/bin/bash");
processBuilder.directory(new File(directory));
Process process = processBuilder.start();
OutputStreamWriter osw = new OutputStreamWriter(process.getOutputStream());
osw.write("rake routes");
osw.close();
printStream(process.getErrorStream());
printStream(process.getInputStream());
}
public static void printStream(InputStream is) throws IOException {
InputStreamReader isr = new InputStreamReader(is);
BufferedReader br = new BufferedReader(isr);
String line;
while ((line = br.readLine()) != null) {
System.out.println(line);
}
}
我知道这是与环境相关的问题,因为这里描述了我遇到的错误 cannot load such file -- bundler/setup (LoadError)
我进一步检查了 processBuilder.environment()
returns 比输入 env
更少的环境变量。我继续更改 osw.write()
行并尝试 echo $GEM_HOME
那里,它不打印任何东西,如果我在我的操作系统上这样做 bash 然后我得到了路径,我也尝试了其他echo $SHELL
之类的常见事物,它在 Java 代码和 bash.
所以我的问题是:
1) 为什么我的操作系统的环境变量与 ProcessBuilder.environment()
方法不同?
2) Process
class 是否考虑使用 ProcessBuilder.environment()
给出的环境变量?如果是这样,那么我们如何从操作系统级别添加缺失的?
1) 您在 java 进程中看到的变量是从您启动 java 进程的进程继承而来的。 IE。如果您从 shell 启动它,它应该具有与 shell 相同的变量。在启动您的 Java 应用程序之前,您需要调查实际设置了哪些变量,以及为什么没有在该上下文中设置您期望的变量。
回答第 2 部分,是的,该过程将在 ProcessBuilder.environment()
中的环境中启动。您可以简单地向 ProcessBuilder.environment()
返回的地图添加内容,这将扩展运行时环境:
ProcessBuilder pb = new ProcessBuilder("foo");
pb.environment().put("MY_VAR", "foobar");