文档章节

七天用Go写个docker(第六天)

o
 osc_zsaazovz
发布于 07/06 11:05
字数 669
阅读 33
收藏 0

行业解决方案、产品招募中!想赚钱就来传!>>>

今天主要来实现一下 go-docker ps 的功能,也就是查看当前有哪些容器,简单说下思路,当我们启动一个容器时就为该容器创建一个文件夹用来保存该容器的一些信息,如果我们给容器指定了名字,那么该文件夹名字就是我们指定的名字,如果未指定,就用我们自动生成的容器ID作为文件夹名,同时在该文件夹中创建config.json用来保存容器信息

文件夹结构

go-docker
└── 容器名/容器ID
    ├── config.json
    └── container.log

  • config.json 记录容器基础信息
  • container.log 记录容器内容日志

记录容器信息

创建容器时,同时给该容器创建一个文件夹,文件夹内并创建config.json 来保存容器信息,这里先看下我们要保存容器哪些信息

type ContainerInfo struct {
	Pid         string   `json:"pid"`     // 容器的init进程再宿主机上的PID
	Id          string   `json:"id"`      // 容器ID
	Command     string   `json:"command"` // 容器内init进程的运行命令
	Name        string   `json:"name"`
	CreateTime  string   `json:"createTime"`
	Status      string   `json:"status"`
	Volume      string   `json:"volume"`      //容器的数据卷
	PortMapping []string `json:"portmapping"` //端口映射
}

看下代码实现,比较简单,一共就3步

  1. 创建以容器名或ID命名的文件夹
  2. 在该文件下创建config.json
  3. 将容器信息保存到config.json中
// 记录容器信息
func RecordContainerInfo(containerPID int, cmdArray []string, containerName, containerID string) error {
	info := &ContainerInfo{
		Pid:        strconv.Itoa(containerPID),
		Id:         containerID,
		Command:    strings.Join(cmdArray, ""),
		Name:       containerName,
		CreateTime: time.Now().Format("2006-01-02 15:04:05"),
		Status:     common.Running,
	}

	dir := path.Join(common.DefaultContainerInfoPath, containerName)
	_, err := os.Stat(dir)
	if err != nil && os.IsNotExist(err) {
		err := os.MkdirAll(dir, os.ModePerm)
		if err != nil {
			logrus.Errorf("mkdir container dir: %s, err: %v", dir, err)
			return err
		}
	}

	fileName := fmt.Sprintf("%s/%s", dir, common.ContainerInfoFileName)
	file, err := os.Create(fileName)
	if err != nil {
		logrus.Errorf("create config.json, fileName: %s, err: %v", fileName, err)
		return err
	}

	bs, _ := json.Marshal(info)
	_, err = file.WriteString(string(bs))
	if err != nil {
		logrus.Errorf("write config.json, fileName: %s, err: %v", fileName, err)
		return err
	}

	return nil
}

遍历容器

简单说下实现逻辑

  1. 遍历 go-docker文件夹
  2. 读取每个容器内的config.json文件
  3. 格式化打印
func ListContainerInfo() {
	files, err := ioutil.ReadDir(common.DefaultContainerInfoPath)
	if err != nil {
		logrus.Errorf("read info dir, err: %v", err)
	}

	var infos []*ContainerInfo
	for _, file := range files {
		info, err := getContainerInfo(file.Name())
		if err != nil {
			logrus.Errorf("get container info, name: %s, err: %v", file.Name(), err)
			continue
		}
		infos = append(infos, info)
	}

	// 打印
	w := tabwriter.NewWriter(os.Stdout, 12, 1, 2, ' ', 0)
	_, _ = fmt.Fprint(w, "ID\tNAME\tPID\tSTATUS\tCOMMAND\tCREATED\n")
	for _, info := range infos {
		_, _ = fmt.Fprintf(w, "%s\t%s\t%s\t%s\t%s\t%s\t\n", info.Id, info.Name, info.Pid, info.Status, info.Command, info.CreateTime)
	}

	// 刷新标准输出流缓存区,将容器列表打印出来
	if err := w.Flush(); err != nil {
		logrus.Errorf("flush info, err: %v", err)
	}
}

// 获取容器内基本信息
func getContainerInfo(containerName string) (*ContainerInfo, error) {
	filePath := path.Join(common.DefaultContainerInfoPath, containerName, common.ContainerInfoFileName)
	bs, err := ioutil.ReadFile(filePath)
	if err != nil {
		logrus.Errorf("read file, path: %s, err: %v", filePath, err)
		return nil, err
	}
	info := &ContainerInfo{}
	err = json.Unmarshal(bs, info)
	return info, err
}
o
粉丝 0
博文 88
码字总数 0
作品 0
私信 提问
加载中
请先登录后再评论。
微信框架的几个层次

第一层次:通信处理 对访问微信服务器进行处理,主要解决报文来来去去的问题。这里采用的技术一般是HttpClient或类似的技术。 第二层次:报文解析 通过对报文进行解析,让程序员直接要拿到的...

悠悠然然
2015/12/01
9.3K
58
Java工程师如何在Docker上进行开发

Java工程师如何在Docker上进行开发?本文能让你以最小的日常开支和预备知识就可以把Docker和Java结合使用。 安装 现在有很多的Java Web框架,挑选一个非常小的框架,选择Spark吧!它是一款基...

dockerer
2015/12/04
8.3K
20
Kubernetes网络分析-Container间通信

本文假设你已经搭建好了Kubernetes集群,那么请求是如何到达POD,然后被Container处理的。都是干货。 如果没听说过Kubernetes,不知道POD是什么,请先参考: http://www.infoq.com/cn/articl...

xue777hua
2015/10/09
4.4K
6
如何写程序自动下载BBC Learning English的所有在线课程

BBC Learning English在线3大系列课程:Lower intermediate、Intermediate、English My Way 声音很悦耳,尤其是Jamaica Inn和The Importance of Being Earnest,堪称完美,百听不厌,这对于英...

杨尚川
2015/10/21
1.9K
3
CentOS 7 YUM 搭建Kubernetes 1.0

Kubernetes 日前终于发布了稳定版 1.0, 本文将要出一个系列的文章来讲述如何搭建环境,部署服务,网络分析,升级服务,备份数据,最后到达如何对Kubernetes进行二次发。 1. CentOS7 YUM 搭建...

xue777hua
2015/09/06
7.8K
14

没有更多内容

加载失败,请刷新页面

加载更多

MySql大表分页(附独门秘技)

问题背景 MySql(InnoDB)中的订单表需要按时间顺序分页查询,且主键不是时间维度递增,订单表在百万以上规模,此时如何高效地实现该需求? 注:本文并非主要讲解如何建立索引,以下的分析均建...

osc_8kei32r9
24分钟前
0
0
css中使用变量

2017年3月,微软宣布 Edge 浏览器将支持 CSS 变量。 这个重要的 CSS 新功能,所有主要浏览器已经都支持了。 声明css变量的时候,变量名前面要加两根连词线(--)。 变量名大小写敏感,--hea...

osc_mpdswsal
25分钟前
0
0
WAS 忘记密码

一、重置密码 1.首先关闭was,ps –ef|grep java 查看java进程号,然后kill -9 XXXX杀掉进程即可。或者使用命令./stopServer.sh server1 2.取消控制台安全验证 方法一:/opt/IBM/WebSphere/...

osc_1i3ltp99
26分钟前
0
0
npm install的--save选项是什么? - What is the --save option for npm install?

问题: I saw some tutorial where the command was: 我看到了一些命令所在的教程: npm install --save What does the --save option mean? --save选项是什么意思? Not able to find the......

fyin1314
26分钟前
5
0
C#使用读写锁三行代码简单解决多线程并发写入文件时线程同步的问题

在开发程序的过程中,难免少不了写入错误日志这个关键功能。实现这个功能,可以选择使用第三方日志插件,也可以选择使用数据库,还可以自己写个简单的方法把错误信息记录到日志文件。 选择最...

osc_7cws6vmd
27分钟前
0
0

没有更多内容

加载失败,请刷新页面

加载更多

返回顶部
顶部