java在docker容器内执行linux命令
最近在项目开发过程中,需要用java去调用windows操作系统和linux操作系统的命令来获取一些计算机信息,执行命令的代码没什么好说的,如下所示:
//windows环境下使用WMIC获取CPU***
//使用WMIC获取CPU***
Process process = Runtime.getRuntime().exec("wmic cpu get processorid");
process.getOutputStream().close();
//如果需要获得执行命令后的返回值,从这个流中获得process.getInputStream()
//linux下获取cpu***
//使用dmidecode命令获取CPU***
String[] shell = {"/bin/bash", "-c", "dmidecode -t processor | grep 'ID' | awk -F ':' '{print $2}' | head -n 1"};
Process process = Runtime.getRuntime().exec(shell);
process.getOutputStream().close();
BufferedReader reader = new BufferedReader(new InputStreamReader(process.getInputStream()));
//TO DO 之后是一些读取操作
OK,这些代码看起来非常好,没什么问题,还根据windwos和linux的情况作了处理。
BUT!你要是把服务直接部署到linux上,用docker启动,那恭喜你就掉进了一个大坑。
通过上面的代码我们不难看懂,JAVA通过
Runtime.getRuntime().exec(“xxxxxx”)
这段代码去运行了dos命令。
正常运行吧倒也没什么问题,重点是docker是个什么东西,它是个容器化技术啊,它只为服务运行提供最低标准的运行环境以降低内存消耗。这里划个重点,最低标准。相当于容器内只有残缺的linux系统和你的服务代码,只要服务的代码能跑起来,我这个系统内其他的东西都是多余的,容器内都不需要,比如说接下来要讲到的dmidecode。
dmidecode是centOS7操作系统内置的工具(对于其他的linux操作系统笔者不了解),用户可用dmidecode命令来查看一些计算机信息。
我们刚才的代码中就用到了dmidecode命令。由于容器内没有dmidecode工具,那么一执行,就嗝屁了。
如果要在docker容器中运行dmidecode命令,那么要将宿主机的如下两个目录挂载到容器中
1:/sbin/dmidecode --这个目录是dmidecode程序的目录,如果不挂载那么容器中识别不了dmidecode命令
2:/dev/mem --dmidecode调用时会使用到mem这个文件,如果不挂载会找不到文件
并且还需要在启动时增加 --privileged 这个参数,让容器获得近似于宿主机root的权限
完整的运行命令如下:
docker run -d -v /sbin/dmidecode:/sbin/dmidecode -v /dev/mem:/dev/mem --name my-tomcat -p 9090:8080 tomcat
(以近似于root的权限用后台模式启动tomcat这个镜像,取别名为my-tomcat,并挂载两个宿主机目录到容器中,将容器的8080端口映射到宿主机9090端口)
总结一下,其实容器中想要用的任何东西,无论是文件还是程序还是什么别的,都可以通过挂载的形式从宿主机中挂载到容器中,让容器中可以访问到。
上一篇: 如何让宿主机访问docker容器内的服务
推荐阅读
-
java在docker容器内执行linux命令
-
在docker中执行linux shell命令的操作
-
工具类:在Java程序中执行Linux命令
-
docker容器内执行docker命令提示Got permission denied while trying to connect to the Docker
-
java实现Linux(centos) 中docker容器下命令交互的代码(配置向导)
-
工具类:在Java程序中执行Linux命令
-
在docker中执行linux shell命令的操作
-
java实现Linux(centos) 中docker容器下命令交互的代码(配置向导)
-
docker宿主机执行某个容器内的某个命令
-
docker在容器外执行容器内的某个命令