如何使用 C# 启动 Java 程序的实时 input/output
How do I get live input/output of a Java program started with C#
我有一个 C# 程序需要执行 Java 程序,但是,当执行 Java 应用程序时,没有显示输出。我还需要这个输出和输入是实时的。
拿这个示例代码:
class Program
{
static void Main(string[] args)
{
Console.WriteLine("Executing \"echo test\":");
EchoRedirectDemo();
Console.WriteLine("Executing \"java -version\":");
JavaRedirectDemo();
}
static void JavaRedirectDemo()
{
ProcessStartInfo processStartInfo = new ProcessStartInfo("java")
{
Arguments = "-version",
RedirectStandardOutput = true,
RedirectStandardError = true,
RedirectStandardInput = true
};
Process process = Process.Start(processStartInfo);
process.WaitForExit();
Console.WriteLine(process.StandardOutput.ReadToEnd());
}
static void EchoRedirectDemo()
{
ProcessStartInfo processStartInfo = new ProcessStartInfo("echo")
{
Arguments = "test",
RedirectStandardOutput = true,
RedirectStandardError = true,
RedirectStandardInput = true
};
Process process = Process.Start(processStartInfo);
process.WaitForExit();
Console.WriteLine(process.StandardOutput.ReadToEnd());
}
}
它将 运行 echo test
很好地重定向 in/out/err,但是 java -v
命令上不会有 in/out/err,如下所示:
Executing "echo test":
test
Executing "java -version":
知道如何解决这个问题吗?
java -version
将在 STDERR 上输出版本信息,而不是 STDOUT。这将要求您在 C# 程序中使用类似 Console.WriteLine(process.StandardError.ReadToEnd());
的东西。
但是,java --version
(注意双破折号)在 STDOUT 上输出版本信息。因此,我建议使用它而不是 java -version
.
(这在 Java 的有关命令行参数的在线文档中也有描述,位于 https://docs.oracle.com/en/java/javase/13/docs/specs/man/java.html)
CliWrap 可以为您简化这个。
using System.Text;
using System;
using CliWrap;
using System.Threading.Tasks;
namespace proj
{
public class Program
{
public static async Task Main(string[] args)
{
var stdOutBuffer = new StringBuilder();
var stdErrBuffer = new StringBuilder();
var result = await Cli.Wrap("java")
.WithArguments("-version")
.WithWorkingDirectory("/")
.WithStandardOutputPipe(PipeTarget.ToStringBuilder(stdOutBuffer))
.WithStandardErrorPipe(PipeTarget.ToStringBuilder(stdErrBuffer))
.ExecuteAsync();
var stdOut = stdOutBuffer.ToString();
var stdErr = stdErrBuffer.ToString();
Console.WriteLine(stdOut);
Console.WriteLine(stdErr);
}
}
}
输出
java version "1.8.0_301"
Java(TM) SE Runtime Environment (build 1.8.0_301-b09)
Java HotSpot(TM) 64-Bit Server VM (build 25.301-b09, mixed mode)
我有一个 C# 程序需要执行 Java 程序,但是,当执行 Java 应用程序时,没有显示输出。我还需要这个输出和输入是实时的。
拿这个示例代码:
class Program
{
static void Main(string[] args)
{
Console.WriteLine("Executing \"echo test\":");
EchoRedirectDemo();
Console.WriteLine("Executing \"java -version\":");
JavaRedirectDemo();
}
static void JavaRedirectDemo()
{
ProcessStartInfo processStartInfo = new ProcessStartInfo("java")
{
Arguments = "-version",
RedirectStandardOutput = true,
RedirectStandardError = true,
RedirectStandardInput = true
};
Process process = Process.Start(processStartInfo);
process.WaitForExit();
Console.WriteLine(process.StandardOutput.ReadToEnd());
}
static void EchoRedirectDemo()
{
ProcessStartInfo processStartInfo = new ProcessStartInfo("echo")
{
Arguments = "test",
RedirectStandardOutput = true,
RedirectStandardError = true,
RedirectStandardInput = true
};
Process process = Process.Start(processStartInfo);
process.WaitForExit();
Console.WriteLine(process.StandardOutput.ReadToEnd());
}
}
它将 运行 echo test
很好地重定向 in/out/err,但是 java -v
命令上不会有 in/out/err,如下所示:
Executing "echo test":
test
Executing "java -version":
知道如何解决这个问题吗?
java -version
将在 STDERR 上输出版本信息,而不是 STDOUT。这将要求您在 C# 程序中使用类似 Console.WriteLine(process.StandardError.ReadToEnd());
的东西。
但是,java --version
(注意双破折号)在 STDOUT 上输出版本信息。因此,我建议使用它而不是 java -version
.
(这在 Java 的有关命令行参数的在线文档中也有描述,位于 https://docs.oracle.com/en/java/javase/13/docs/specs/man/java.html)
CliWrap 可以为您简化这个。
using System.Text;
using System;
using CliWrap;
using System.Threading.Tasks;
namespace proj
{
public class Program
{
public static async Task Main(string[] args)
{
var stdOutBuffer = new StringBuilder();
var stdErrBuffer = new StringBuilder();
var result = await Cli.Wrap("java")
.WithArguments("-version")
.WithWorkingDirectory("/")
.WithStandardOutputPipe(PipeTarget.ToStringBuilder(stdOutBuffer))
.WithStandardErrorPipe(PipeTarget.ToStringBuilder(stdErrBuffer))
.ExecuteAsync();
var stdOut = stdOutBuffer.ToString();
var stdErr = stdErrBuffer.ToString();
Console.WriteLine(stdOut);
Console.WriteLine(stdErr);
}
}
}
输出
java version "1.8.0_301"
Java(TM) SE Runtime Environment (build 1.8.0_301-b09)
Java HotSpot(TM) 64-Bit Server VM (build 25.301-b09, mixed mode)