Java9 进程API
来源:互联网 发布:office mac 破解 威锋 编辑:程序博客网 时间:2024/06/05 18:59
1. 概述
Java中的进程API在Java5之前还是非常原始的,开启一个新进程唯一的方式是调用Runtime.getRuntime().exec()
,直到Java5发布之后,一些更加简明的开启新进程方式被封装到了ProcessBuilder
中。
而在Java9中,你也将能使用一种全新的方式来获取当前系统所有正在运行的进程的相关信息。
话不多说,先睹为快!
2. 当前Java进程的信息
我们通过调用java.lang.ProcessHandle.Info
可以获取诸多进程的相关信息:
- 用于开启此进程所使用的命令
- 命令中传递的参数
- 开启时间
- 开启者和总运行时间
下面是具体方式:
@Testpublic void givenCurrentProcess_whenInvokeGetInfo_thenSuccess() throws IOException { ProcessHandle processHandle = ProcessHandle.current(); ProcessHandle.Info processInfo = processHandle.info(); assertNotNull(processHandle.getPid()); assertEquals(false, processInfo.arguments().isPresent()); assertEquals(true, processInfo.command().isPresent()); assertTrue(processInfo.command().get().contains("java")); assertEquals(true, processInfo.startInstant().isPresent()); assertEquals(true, processInfo.totalCpuDuration().isPresent()); assertEquals(true, processInfo.user().isPresent());}
需要注意的是,java.lang.ProcessHandle.Info
是在另一个接口java.lang.ProcessHandle
中定义的公共接口。JDK 供应商(Oracle JDK, Open JDK, Zulu 或其他) 以上面这些方式来为接口提供实现,以使它们能返回进程的相关信息。
3. 产生进程的信息
我们也可以获取新产生的进程的相关信息。在此情况下,在我们调用java.lang.Process
生成并获取一个进程之后,我们调用toHandle()
方法来获取java.lang.ProcessHandle
的实例。
其他细节与上例一致:
String javaCmd = ProcessUtils.getJavaCmd().getAbsolutePath();ProcessBuilder processBuilder = new ProcessBuilder(javaCmd, "-version");Process process = processBuilder.inheritIO().start();ProcessHandle processHandle = process.toHandle();
4. 枚举系统中的实时进程
我们可以列举出当前系统中的所有进程,这些进程对当前进程可见。返回的列表是调用API时的快照,因此在操作的同时可能有进程终止,也可能有新的进程被开启。
我们可以使用java.lang.ProcessHandle
接口中声明的静态方法allProcesses()
来获取ProcessHandle
流:
@Testpublic void givenLiveProcesses_whenInvokeGetInfo_thenSuccess() { Stream<ProcessHandle> liveProcesses = ProcessHandle.allProcesses(); liveProcesses.filter(ProcessHandle::isAlive) .forEach(ph -> { assertNotNull(ph.getPid()); assertEquals(true, ph.info() .command() .isPresent()); });}
5. 枚举子进程
这里有两种获取方式:
- 获取当前进程的直属子级
- 获取当前进程的所有子级
前者调用children()
,后者调用descendants()
:
@Testpublic void givenProcess_whenGetChildProcess_thenSuccess() throws IOException{ int childProcessCount = 5; for (int i = 0; i < childProcessCount; i++){ String javaCmd = ProcessUtils.getJavaCmd() .getAbsolutePath(); ProcessBuilder processBuilder = new ProcessBuilder(javaCmd, "-version"); processBuilder.inheritIO().start(); } Stream<ProcessHandle> children = ProcessHandle.current().children(); children.filter(ProcessHandle::isAlive) .forEach(ph -> log.info("PID: {}, Cmd: {}", ph.getPid(), ph.info().command())); // and for descendants Stream<ProcessHandle> descendants = ProcessHandle.current().descendants(); descendants.filter(ProcessHandle::isAlive) .forEach(ph -> log.info("PID: {}, Cmd: {}", ph.getPid(), ph.info().command()));}
6. 进程终止时触发相关操作
有时候有需求需要我们在某个进程终止时触发某些操作,我们可以通过调用java.lang.ProcessHandle
接口中声明的onExit()
方法来满足。 该方法返回CompletableFuture
,可以在CompletableFuture
完成时触发某些操作。
CompletableFuture
表示一个进程已经完成,它不关心进程以何种方式完成。通过显式调用它的get()
方法来等待进程完成:
@Testpublic void givenProcess_whenAddExitCallback_thenSuccess() throws Exception { String javaCmd = ProcessUtils.getJavaCmd() .getAbsolutePath(); ProcessBuilder processBuilder = new ProcessBuilder(javaCmd, "-version"); Process process = processBuilder.inheritIO() .start(); ProcessHandle processHandle = process.toHandle(); log.info("PID: {} has started", processHandle.getPid()); CompletableFuture<ProcessHandle> onProcessExit = processHandle.onExit(); onProcessExit.get(); assertEquals(false, processHandle.isAlive()); onProcessExit.thenAccept(ph -> { log.info("PID: {} has stopped", ph.getPid()); });}
当然,也可以通过java.lang.Process
接口来调用onExit()
方法。
原文:http://www.baeldung.com/java-9-process-api
- Java9 进程API
- Java9 进程API详细介绍
- java9新特性-Process 进程 API
- JAVA9 API文档地址
- Java9新API--Collections、Streams
- Java9
- java9
- java9
- Java9
- JAVA9
- JAVA9
- Java9 HTTP2.0 API入门与实践
- Java9 HTTP2.0 API入门与实践
- JAVA9 API翻译(Module java.activation)
- JAVA9 API翻译(Module java.base)
- java9-String
- java9-1
- HealthInfo.java9
- jsp页面加减及小计总计
- 心理咨询室微信预约系统——乐享其约新品
- 自动轮播js轮播图 简单实用!!!
- 基于ssm的场地管理系统
- 泛型
- Java9 进程API
- Spring 学习(三)注解装配
- Gym 101512K
- LeetCode Week3
- 学习VUE2.0入门到进阶路线推荐
- 聚类和EM算法
- 利用ztree实现树搜索
- TCP和UDP的区别
- Unity Movement AI (二)