ProcessBuilder – 启动另一个进程/ JVM – HowTo?
我正在编写一个网络应用程序,其中每个客户端都有一个Singleton ClientManager。 为了测试 ,我想创建几个客户端(每个客户端都在自己的VM /进程中),而不是手动启动程序n次。
有关stackoverflow的以下两个问题已经描述了如何做到这一点:
- 这真的是从Java代码启动第二个JVM的最佳方法吗?
- Java:在单独的进程中执行Java应用程序
我的代码基于这些,但它不起作用:
- 调用spawn后,主程序不会继续。
- 生成的代码不会被执行。
这是使用ProcessBuilder的完整代码:
public class NewVM { static class HelloWorld2 { public static void main(String[] args) { System.out.println("Hello World"); System.err.println("Hello World 2"); } } public static void main(String[] args) throws Exception { startSecondJVM(HelloWorld2.class, true); startSecondJVM(HelloWorld2.class, false); System.out.println("Main"); } public static void startSecondJVM(Class clazz, boolean redirectStream) throws Exception { System.out.println(clazz.getCanonicalName()); String separator = System.getProperty("file.separator"); String classpath = System.getProperty("java.class.path"); String path = System.getProperty("java.home") + separator + "bin" + separator + "java"; ProcessBuilder processBuilder = new ProcessBuilder(path, "-cp", classpath, clazz.getCanonicalName()); processBuilder.redirectErrorStream(redirectStream); Process process = processBuilder.start(); process.waitFor(); System.out.println("Fin"); } }
我究竟做错了什么???
BTW:
- 我正在使用Eclipse。
- Singleton问题是一个简化的例子。 请不要建议创建工厂。
解决方案: HelloWorld2不能是内部类。
我建议你让HelloWorld2成为顶级课程。 看来java期待一个顶级课程。
这是我试过的代码。
class Main { static class Main2 { public static void main ( String [ ] args ) { System . out . println ( "YES!!!!!!!!!!!" ) ; } } public static void main ( String [ ] args ) { System . out . println ( Main2 . class . getCanonicalName ( ) ) ; System . out . println ( Main2 . class . getName ( ) ) ; } } class Main3 { public static void main ( String [ ] args ) { System . out . println ( "YES!!!!!!!!!!!" ) ; } }
- getCanonicalName和getName返回不同的名称。 哪一个是对的? 他们都错了。
- Main3有效。
我认为我看到了部分问题的修复: process.waitFor()
阻止控制在子process.waitFor()
结束之前返回main()。
为了弄清楚你的生成进程没有启动的原因,我建议打印出ProcessBuilder
构造函数的所有参数,并检查用这些参数调用的手动调用的JVM是否成功。 特别是,您需要将该类名称作为具有static void main(String[])
的类的名称。