---
title: "Docker"
author: "Perrin Yong"
author_profile: https://www.pystone.net/profile/
published_by: "Perrin Yong"
canonical: https://www.pystone.net/notes/docker-basics/
type: note
content_role: unspecified
visibility: public
id_stability: rename-stable
source_path: "10-计算机、信息技术与工程/03-软件工程与质量保障/CI-CD与质量保障/CI-CD工具链/Docker.md"
content_hash: fc5aec1c43694c92c938fe4f0df0430e0ba71e21102247fe6088de1b2a0b0315
knowledge_version: 224c990773de.5fa8af6e39fa
site_commit: 224c990773de166d23a886306577dd90379529ce
notes_commit: 5fa8af6e39fa3891d1b9b4832bfa6c4e0ecaaf0a
---
# Docker

> 创建时间：2020/11/15 18:01

  * Docker
    * Overview
      * 是什么
        * 核心概念
        * 其他相关概念
      * 为什么用
        * 虚拟机
        * Linux 容器
        * Docker
        * 其他解释
      * 用途
    * 原理
    * 用法
      * image 文件
      * container 文件
      * docker-compose
      * 命令
      * Dockerfile
    * 一些坑
      * wsl启动失败
    * Ref

## Overview

### 是什么

dock: 船坞，码头 docker: 码头工人
Docker本身并不是容器，它是创建容器的工具，是应用容器引擎。

在一艘大船上，可以把货物规整的摆放起来。并且各种各样的货物被 **集装箱** 标准化了，集装箱和集装箱之间不会互相影响。

  * Build, Ship and Run (搭建、发送、运行)

  * Build once，Run anywhere（搭建一次，到处能用）

Docker 属于 Linux 容器的一种封装，提供简单易用的容器使用接口。它是目前最流行的 Linux 容器解决方案。

Docker 将应用程序与该程序的依赖，打包在一个文件里面。运行这个文件，就会生成一个虚拟容器。程序在这个虚拟容器里运行，就好像在真实的物理机上运行一样。有了 Docker，就不用担心环境问题。

#### 核心概念

镜像（Image）
容器（Container）
仓库（Repository）

#### 其他相关概念

**LXC** \- Linux容器虚拟技术（Linux container）

**PaaS** \- **Platform as a service** (PaaS) or application platform as a service (aPaaS) or platform-based service is a category of cloud computing services that provides a platform allowing customers to develop, run, and manage applications without the complexity of building and maintaining the infrastructure typically associated with developing and launching an app.

**WSL** \- The Windows Subsystem for Linux lets developers run a GNU/Linux environment – including most command-line tools, utilities, and applications – directly on Windows, unmodified, without the overhead of a traditional virtual machine or dualboot setup.

### 为什么用

#### 虚拟机

虚拟机 - 在一种操作系统里面运行另一种操作系统，用户可以通过虚拟机还原软件的原始环境。

缺点：资源占用多，冗余步骤多启动慢

#### Linux 容器

LXC - Linux容器虚拟技术（Linux container）。不是模拟一个完整的操作系统，而是对进程进行隔离，只需要虚拟一个小规模的环境（类似“沙箱”）。或者说，在正常进程的外面套了一个保护层。对于容器里面的进程来说，它接触到的各种资源都是虚拟的，从而实现与底层系统的隔离。

优点：启动快，资源占用少，体积小

#### Docker

Docker 属于 Linux 容器的一种封装，提供简单易用的容器使用接口。除了运行容器之外，Docker 技术还具备其他多项功能，包括简化用于构建容器、传输镜像以及控制镜像版本的流程。

> 虚拟机属于虚拟化技术。而Docker这样的容器技术，也是虚拟化技术，属于轻量级的虚拟化。

  * 启动时间很快，几秒钟就能完成

  * 对资源的利用率很高（一台主机可以同时运行几千个Docker容器）

  * 它占的空间很小，虚拟机一般要几GB到几十GB的空间，而容器只需要MB级甚至KB级

> 总体来说，Docker 的接口相当简单，用户可以方便地创建和使用容器，把自己的应用放入容器。容器还可以进行版本管理、复制、分享、修改，就像管理普通的代码一样。

#### 其他解释

  1. 不同的应用程序可能会有不同的应用环境，把他们依赖的软件都安装在一个服务器上就要调试很久，而且很麻烦，还会造成一些冲突。我们可以在服务器上创建不同的虚拟机在不同的虚拟机上放置不同的应用，但是虚拟机开销比较高。docker可以实现虚拟机隔离应用环境的功能，并且开销比虚拟机小，小就意味着省钱了。

  2. 你开发软件的时候用的是Ubuntu，但是运维管理的都是centos，运维在把你的软件从开发环境转移到生产环境的时候就会遇到一些Ubuntu转centos的问题，比如：有个特殊版本的数据库，只有Ubuntu支持，centos不支持，在转移的过程当中运维就得想办法解决这样的问题。这时候要是有docker你就可以把开发环境直接封装转移给运维，运维直接部署你给他的docker就可以了。而且部署速度快。

  3. 在服务器负载方面，如果你单独开一个虚拟机，那么虚拟机会占用空闲内存的，docker部署的话，这些内存就会利用起来。

Docker 既易于使用，又别具一格——它可为用户提供前所未有的高度应用程访问权限、快速部署以及版本控制和分发能力。

### 用途

（1）提供一次性的环境。比如，本地测试他人的软件、持续集成的时候提供单元测试和构建的环境。
（2）提供弹性的云服务。因为 Docker 容器可以随开随关，很适合动态扩容和缩容。
（3）组建微服务架构。通过多个容器，一台机器可以跑多个服务，因此在本机就可以模拟出微服务架构。

## 原理

使用 Linux 内核和内核功能（例如 Cgroups 和 namespaces）来分隔进程，以便各进程相互独立运行。这种独立性正是采用容器的目的所在；它可以独立运行多种进程、多个应用，更加充分地发挥基础设施的作用，同时保持各个独立系统的安全性。

## 用法

<https://docs.docker.com/docker-for-windows/install-windows-home/>

### image 文件

Docker 把应用程序及其依赖，打包在 image 文件里面。只有通过这个文件，才能生成 Docker 容器。image 文件可以看作是容器的模板。Docker 根据 image 文件生成容器的实例。同一个 image 文件，可以生成多个同时运行的容器实例。

image 是二进制文件。实际开发中，一个 image 文件往往通过继承另一个 image 文件，加上一些个性化设置而生成。举例来说，你可以在 Ubuntu 的 image 基础上，往里面加入 Apache 服务器，形成你的 image。

### container 文件

image 文件生成的容器实例，本身也是一个文件，称为容器文件。也就是说，一旦容器生成，就会同时存在两个文件： image 文件和容器文件。而且关闭容器并不会删除容器文件，只是容器停止运行而已。

```cpp
string str1 = &quot;test&quot;;
string str2 = &quot;test&quot;;

```

终止运行的容器文件，依然会占据硬盘空间，可以使用以下命令删除。

```cpp
string str1 = &quot;test&quot;;
string str2 = &quot;test&quot;;

```

### docker-compose

Docker 镜像在创建之后，往往需要自己手动 pull 来获取镜像，然后执行 run 命令来运行。当服务需要用到多种容器，容器之间又产生了各种依赖和连接的时候，部署一个服务的手动操作是令人感到十分厌烦的。

dcoker-compose 技术，就是通过一个 .yml 配置文件，将所有的容器的部署方法、文件映射、容器连接等等一系列的配置写在一个配置文件里，最后只需要执行 docker-compose up 命令就会像执行脚本一样的去一个个安装容器并自动部署他们，极大的便利了复杂服务的部署。

### 命令

```cpp
string str1 = &quot;test&quot;;
string str2 = &quot;test&quot;;

```

hello world输出这段提示以后，就会停止运行，容器自动终止。

有些容器不会自动终止，因为提供的是服务。比如，安装运行 Ubuntu 的 image，就可以在命令行体验 Ubuntu 系统。

```cpp
string str1 = &quot;test&quot;;
string str2 = &quot;test&quot;;

```

对于那些不会自动终止的容器，必须使用docker container kill 命令手动终止。

```cpp
string str1 = &quot;test&quot;;
string str2 = &quot;test&quot;;

```

### Dockerfile

它是一个文本文件，用来配置 image。Docker 根据 该文件生成二进制的 image 文件。

## 一些坑

### wsl启动失败

Switch to Linux containers时报错：

```cpp
string str1 = &quot;test&quot;;
string str2 = &quot;test&quot;;

```

在cmd中输入 bash 或者 wsl 都报错， 提示 - 参考的对象类型不支持尝试的操作。

解决方法：
以管理员身份运行CMD，执行 `netsh winsock reset`

再输入wsl即可正常运行。启动docker-desktop，也可正常使用Linux containers

> 其他方案：<https://blog.csdn.net/guoxingege/article/details/108983329>

## Ref

<https://www.zhihu.com/question/28300645>
<http://www.ruanyifeng.com/blog/2018/02/docker-tutorial.html>
<https://www.redhat.com/zh/topics/containers/what-is-docker>
