实现思路

通过在运行docker容器的系统中安装ssh、sshpass服务,编写ssh连接到宿主机脚本,同时携带在宿主机中需要执行的命令,来达到在容器中获取宿主机执行命令的返回值的效果。因此这里有一个前提,必须知道宿主机的IP地址,如果在执行脚本时不知道宿主机IP地址,可以在项目中添加一个手动配置宿主机IP地址的功能,当然这是要根据功能来定的。


安装ssh服务

lz使用的镜像是centos的官方镜像,具体安装方式可以自行百度

  • 安装ssh服务
 yum -y install openssh-server


更改ssh服务配置,将PermitRootLogin的值修改为yes保存退出,如果是yes的话不需要修改

vim /etc/ssh/sshd_config

启动ssh服务

systemctl start sshd.service

设置ssh服务开机自启

systemctl enable sshd.service

查看ssh状态

systemctl status sshd.service

测试格式,输入完成后如果提示输入目标服务器密码即代表安装完成

ssh -p 22 root@IP地址


安装sshpass -

yum -y install sshpass

测试指令是否可以使用
格式:sshpass -p '宿主机密码' ssh -o StrictHostKeyChecking=no -p 22 root@宿主机IP地址 df -h

此时已经可以读取到宿主机的磁盘信息了,如果你想执行其他命令,可以把df -h换成你想在宿主机中执行的命令


编写脚本 -

vim runningContainerInfo.sh

添加内容,记得将密码改成自己的

:<<!
sshpass 携带ssh连接时的密码,避免使用ssh连接时第二次输入密码(20101111为宿主机root账号密码)
StrictHostKeyChecking=no 避免第一次连接时需要输入密码
$1 宿主机IP地址脚本执行格式:sh /root/runningContainerInfo.sh 192.168.0.1
192.168.0.1是宿主机IP地址
!
sshpass -p '20101111' ssh -o StrictHostKeyChecking=no  -p 22 root@$1 docker ps

启动脚本

sh /root/runningContainerInfo.sh 192.168.0.196

编写程序执行脚本

@ResponseBody@GetMapping("/testInDockerGetHostInfo")public ResponseResult testInDockerGetHostInfo(String command) {// sshpass -p "20100514" ssh -p 22 root@192.168.0.196 commandlog.info("开始执行Linux命令:【{}】", command);String[] split = command.split(" ");List<String> cmd = Arrays.asList(split);ProcessBuilder builder = new ProcessBuilder(cmd);log.info("command命令:{}", cmd.toString());try {Process start = builder.start();try {start.waitFor();} catch (InterruptedException e) {e.printStackTrace();}BufferedReader br2 = new BufferedReader(new InputStreamReader(start.getErrorStream()));StringBuilder buf = new StringBuilder(); // 保存输出结果流String line;while ((line = br2.readLine()) != null) buf.append(line); //log.info("******获取宿主机错误信息:{}******", buf.toString());BufferedReader or2 = new BufferedReader(new InputStreamReader(start.getInputStream()));StringBuilder ouf = new StringBuilder(); // 保存输出结果流String line1;while ((line1 = or2.readLine()) != null) ouf.append(line1); //log.info("******获取宿主机正常输出信息:{}******", ouf.toString());} catch (IOException e) {e.printStackTrace();}return new ResponseResult<String>();}

浏览器访问信息command参数值为你现在宿主机执行的指令,lz这样写是为了测试的时候比较方便,但实际项目中不建议因为不安全,可以直接执行任意linux命令,最好将command参数去掉,接口中确定command命令


日志信息,lz的脚本命令如下,作用是获取宿主机上运行中的镜像名称为luntek/ic-platform,然后获取每一行数据的第1和28列数据,再除去容器名称为ic的列,最后只获取第一列的数据即得到运行中容器的ID,用来下一步停止正在运行的其他容器

sshpass -p '我的密码' ssh -o StrictHostKeyChecking=no  -p 22 root@$1 docker ps | grep luntek/ic-platform |awk -F ' ' '{print $1,$28}'| grep -v "\<ic\>" |awk -F ' ' '{print $1}'

贴一下宿主机docker ps的输出图

最后输出了容器ic01和ic058的容器ID,后面可以用来终止容器

|为管道符,可以理解成将管道符前面的返回值基础上再次操作,具体的grep和awk的指令可以参考下面链接
linux下awk命令详解
grep命令详解


解决这个问题之前也尝试过网上的很多种方法,但觉得依旧不是很方便,然后查阅很多资料后突然想到这个方法,尝试了大约一两天才完全解决这个问题,希望大家能支持一下,原创

来生还长,切勿惆怅;创作不易,随手点赞 ^_^


****************************20211120补充****************************
今天将对应的脚本移到另外的镜像中运行后发现没有反应,于是将脚本中的指令取出来单独运行发现还是同样的问题,找了一下原因,后来通过更新yum后和重新安装sshpass解决这个问题
更新yum:

sudo yum clean all
sudo yum makecache
sudo yum update -y

获取硬盘序列号

 diskdata=`fdisk -l`diskleft=${diskdata#*"identifier: "}identifier=${diskleft%%" Device Boot"*}echo ${identifier}

获取MAC地址

 macAddress=`ifconfig | awk -F'[ :]+' '!NF{if(eth!=""&&ip=="")print eth;eth=ip4=""}/^[^ ]/{eth=$1}/inet addr:/{ip=$4}'`ifconfig ${macAddress[]} | grep "ether" | awk '{print $2}'

docker容器中获取宿主机任意信息相关推荐

  1. 【Docker】docker容器内获取宿主机的信息和执行宿主机的脚本

    思路 我们可以通过在容器内远程连接宿主机,然后对宿主机进行操作. 使用 sshpass (我的是CentOS 7.9环境) 1.安装sshpass apt-get update //更新一下 apt- ...

  2. 17.Docker 容器时间与宿主机同步

    Docker容器时间与宿主机同步 BY 赫墨拉 · PUBLISHED 2018年7月10日 · UPDATED 2019年6月10日 问题描述: 在我们平时使用docker,运行我们的应用的时候,访 ...

  3. docker容器无法访问宿主机报出 No route to host

    项目场景: 提示:docker容器无法访问宿主机报出 No route to host: 例如:防火墙环境下,docker容器无法访问宿主机的其他应用端口 原因分析: 在进行docker部署的时候我们 ...

  4. Docker容器时间与宿主机不一致?3个解决方案

    目录 前言 更新历史 问题描述 解决方案 docker run 添加时间参数 Dockerfile解决方案 docker-compose解决方案 宿主机直接执行命令给某个容器同步时间 异常问题 Doc ...

  5. Docker容器时间与宿主机同步

    转载地址:http://www.louisvv.com/archives/1716.html 问题描述: 在我们平时使用docker,运行我们的应用的时候,访问应用页面的时间与现在相差8个小时 无法结 ...

  6. docker容器端口影射宿主机端口

    #将容器的8080端口映射宿主机端口8080 –name:给容器起的名称 docker run -d -p 8080:8080 --name="tomcat7" -id 1130e ...

  7. docker容器时区与宿主机不一致的解决方法

    一般情况下,我们的宿主机服务器的时区都是在东八区,而docker容器里却是在零时区.这样就导致了时间差了8个小时,所以需要把容器的时间也设置成东八区. 在dockerfile中的设置如下: RUN l ...

  8. docker容器正常启动宿主机却无法正常访问

    问题:重新开启linux虚拟机后有时候可以访问有时候不可以访问docker容器或者完全无法访问 原因:linux内核版本和docker版本不兼容 解决:更新linux内核版本 yum update - ...

  9. docker网络问题解决办法“大全”:关于宿主机访问不了docker容器中web服务,或者容器内访问不了外网的问题的解决办法

    docker网络问题解决办法"大全":关于宿主机访问不了docker容器中web服务,或者容器内访问不了外网的问题的解决办法 参考文章: (1)docker网络问题解决办法&quo ...

  10. Docker中创建MySQL容器,将宿主机目录直接挂载到目录

    Docker中创建MySQL容器,将宿主机目录直接挂载到目录 1.在Docker中下载MySQL镜像 docker pull mysql:5.7.25 2.创建目录/tmp/mysql/data和/t ...

最新文章

  1. 一文读懂经典双目稠密匹配算法SGM
  2. Unix实用工具教程:《sed与awk》修订第三版清晰版
  3. java dom 解析xml 例子,Java DOM解析XML的幾個例子
  4. SVD分解算法及其应用
  5. 怎么提高自己的系统架构水平
  6. matlab中Folder是什么意思,matlab – @folder和文件夹
  7. 【C语言】求N的阶乘
  8. 描述linux shell中单引号,linux shell中单引号、双引号、反引号、反斜杠的区别
  9. is not backed by gradle android,Module … is not backed by gradle
  10. google sdk speech-to-text(谷歌语音转文本、谷歌语音转字幕)
  11. avplayer视频重复循环播放,视频重播
  12. 数据库中的 【行式存储】和【列式存储】
  13. 自动驾驶仿真时如何采集数据做地图
  14. Adversarial Attack on Attackers: Post-Process to Mitigate Black-Box Score-Based Query Attacks
  15. 2022年最新吉林道路运输安全员模拟真题题库及答案
  16. Android 自动亮度
  17. 极智开发 | 昇腾atlas300 docker开发环境搭建
  18. 查看网站历史记录的2种办法,怎样查看网站历史记录?
  19. chrome和firefox在linux,我为什么使用Firefox浏览器而不是Chrome
  20. Java版色情图像过滤入门示例及源码-0.1.0 (模拟绿坝过滤机制)

热门文章

  1. C、C++中出现nan、inf原因
  2. android anr 分析方法,Android ANR分析
  3. WPS-Word:下一页分节符不能分页,插入下一页分节符时下一节没有在新的一页开始
  4. Unity3D开发:向Unity3D中导入外部模型
  5. 【转】鼠标右键多余菜单清理
  6. yarn : 无法加载文件 C:\Users\Emily\AppData\Roaming\npm\yarn.ps1,因为在此系统上禁止运行脚本。
  7. 浅谈视频会议系统的带宽控制!
  8. flash 围棋_围棋怎么玩,最还有flash
  9. ld.exe: cannot find -l?eclipse上用C/C++时,如何链接静态库?
  10. MAC Mail签名添加图片,不显示为附件操作