![](/img/trans.png)
[英]java.io.IOException: Cannot run program “/usr/bin/sh”: java.io.IOException: error=2, No such file or directory
[英]java.io.IOException: Cannot run program “…”: java.io.IOException: error=2, No such file or directory
我需要从 Java 执行一个外部程序(使用 libreoffice 将fodt文件转换为pdf ,它确实发生了)我知道我需要该程序的精确命令行:
/usr/bin/libreoffice --headless --convert-to pdf:'writer_pdf_Export' --outdir /home/develop/tomcat/mf/ROOT/private/docs/0/ /home/develop/tomcat/mf/ROOT/private/docs/0/35_invoice.fodt
这在命令行中完美运行。 但它在使用ProcessBuilder
Java 中不起作用:
java.io.IOException: Cannot run program "/usr/bin/libreoffice --headless --convert-to pdf:'writer_pdf_Export' --outdir /home/develop/tomcat/mf/ROOT/private/docs/0 /home/develop/tomcat/mf/ROOT/private/docs/0/35_invoice.fodt": java.io.IOException: error=2, No such file or directory
我尝试了一些不同的方法但没有成功。 这是上次测试的示例
List<String> command = new ArrayList<String>();
command.add("/usr/bin/libreoffice");
command.add("--headless");
command.add("--convert-to pdf:'writer_pdf_Export' --outdir " + getDestinationDirectory(order) + " " + getInvoiceFilename() + ".fodt");
ProcessBuilder builder = new ProcessBuilder(command);
Process process = null;
try {
process = builder.start();
} catch (IOException ex) {
Logger.getLogger(Documents.class.getName()).log(Level.SEVERE, null, ex);
}
InputStream is = process.getInputStream();
InputStreamReader isr = new InputStreamReader(is);
BufferedReader br = new BufferedReader(isr);
String line;
try {
while ((line = br.readLine()) != null) {
System.out.println(line);
}
} catch (IOException ex) {
Logger.getLogger(Documents.class.getName()).log(Level.SEVERE, null, ex);
}
System.out.println("Program terminated!");
ProcessBuilder
构造函数要求外部程序的每个参数都是独立的(以数组或String
List
的形式)。 你得到的第一条异常消息,
Cannot run program "/usr/bin/libreoffice --headless --convert-to pdf:'writer_pdf_Export' --outdir /home/develop/tomcat/mf/ROOT/private/docs/0 /home/develop/tomcat/mf/ROOT/private/docs/0/35_invoice.fodt"
并没有抱怨它可以找到一个名为/usr/bin/libreoffice
。 它抱怨它找不到一个名字很长很奇特的程序“ /usr/bin/libreoffice --headless --convert-to pdf:'writer_pdf_Export' --outdir /home/develop/tomcat/mf/ROOT/private/docs/0 /home/develop/tomcat/mf/ROOT/private/docs/0/35_invoice.fodt
",因为您将参数连接成一个String
。
代替
command.add("--convert-to pdf:'writer_pdf_Export' --outdir " + getDestinationDirectory(order) + " " + getInvoiceFilename() + ".fodt")
诸如此类,将每个参数拆分为自己对List.add
的调用
command.add("--convert-to");
command.add("pdf:writer_pdf_Export");
command.add("--outdir");
command.add(getDestinationDirectory(order).toString());
command.add(getInvoiceFilename() + ".fodt");
请注意,“writer_pdf_Export”周围没有撇号,因为它们是 shell 元字符,并且在构建数组以传递给没有中间 shell 的exec
不需要。
试试这个(保持简单)...
Process p = Runtime.getRuntime().exec("/usr/bin/libreoffice --headless --convert-to pdf:'writer_pdf_Export' --outdir "+ getDestinationDirectory(order)+" "+getInvoiceFilename()+".fodt");
完全...
Process process = null;
try {
process = Runtime.getRuntime().exec("/usr/bin/libreoffice --headless --convert-to pdf:'writer_pdf_Export' --outdir "+ getDestinationDirectory(order)+" "+getInvoiceFilename()+".fodt");
} catch (IOException ex) {
Logger.getLogger(Documents.class.getName()).log(Level.SEVERE, null, ex);
}
BufferedReader br = new BufferedReader(new InputStreamReader(process.getInputStream()));
String line;
try {
while ((line = br.readLine()) != null) {
System.out.println(line);
}
} catch (IOException ex) {
Logger.getLogger(Documents.class.getName()).log(Level.SEVERE, null, ex);
}
br.close();
System.out.println("Program terminated!");
我已经尝试了这个线程中提出的所有解决方案,但它不起作用。
在我的应用程序(在 linux 中使用 TOMCAT 的 java webapp)中,它只能创建一个 shell 脚本并执行该脚本。 但是你必须在脚本中放置绝对路径,如果没有,它不起作用($HOME 不起作用)。 此外,您可以向它传递参数。
例子:
Runtime.getRuntime().exec("/home/user/myscript.sh param1");
声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.