Docker入門

来源:https://www.cnblogs.com/hwlong/archive/2018/11/23/9961716.html
-Advertisement-
Play Games

[TOC] 一、Docker介紹 1.1 什麼是Docker ​ Docker是一個開源的應用容器引擎,使用Go語言開發,基於Linux內核的cgroup,namespace,Union FS等技術,對應用進程進行封裝隔離,並且獨立於宿主機與其他進程,這種運行時封裝的狀態稱為容器。 ​ Docker ...


目錄

一、Docker介紹

1.1 什麼是Docker

​ Docker是一個開源的應用容器引擎,使用Go語言開發,基於Linux內核的cgroup,namespace,Union FS等技術,對應用進程進行封裝隔離,並且獨立於宿主機與其他進程,這種運行時封裝的狀態稱為容器。

​ Docker早期版本實現是基於LXC,併進一步對其封裝,包括文件系統、網路互聯、鏡像管理等方面,極大簡化了容器管理。從0.7版本以後開始去除LXC,轉為自省研發的libcontainer,從1.11版本開始,進一步為使用runC和containerd。

​ Docker理念是將應用及依賴包打包到一個可移植的容器中,可發佈到任意Linux發行版Docker引擎上。使用沙箱機制運行程式,程式之間相互隔離。

1.2 Docker體繫結構

Containerd:是一個簡單的守護進程,使用runC管理容器。向Docker Engine提供介面。

Shim:只負責管理一個容器。

runC:是一個輕量級的工具,只用來運行容器。

  • Docker Client:客戶端
  • Docker Daemon:守護進程
  • Docker Images:鏡像
  • Docker Container:容器
  • Docker Registry:鏡像倉庫

1.3 Docker內部組件

  • Namespaces
命名空間,Linux內核提供的一種對進程資源隔離的機制,例如進程、網路、掛載點等資源。
  • CGroup
控制組,Linux內核提供的一種限制進程資源的機制;例如CPU、記憶體等資源。
  • UnionFS
聯合文件系統,支持將不同位置的目錄掛載到同一虛擬文件系統,形成一種分層的模型。

1.4 什麼是容器?

  • 對軟體和其依賴的標準化打包
  • 應用之間相互隔離
  • 共用同一個OS Kernel
  • 可以運行在很多主流操作系統上

1.5 容器和虛擬機的區別

以KVM為例與Docker對比

  • 啟動時間
Docker妙級啟動,KVM分鐘級啟動。
  • 輕量級
容器鏡像帶下通常以M為單位,虛擬機以G為單位。
容器資源占用小,要比虛擬機部署更快捷。
  • 性能
容器共用宿主機內核,系統級虛擬化,占用資源少,沒有Hypervisor層開銷,容器性能基本接近物理機;
虛擬機需要Hypervisior層支持,虛擬化一些設備,具備完整的GuestOS,虛擬化開銷大,因而降低性能,沒有容器性能好。
  • 安全性
由於共用宿主機內核,只是進程級隔離,因此隔離性和穩定性不如虛擬機,容器具有一定許可權訪問宿主機內核,存在一定安全隱患。
  • 使用要求
KVM基於硬體的完全虛擬化、需要贏家CPU虛擬化技術支持;
容器共用所主機內核,可運行在主流的Linux發行版,不用考慮CPU是否支持虛擬化技術。

1.6 虛擬化+容器

二、Docker安裝

2.1 Docker官方網站

https://wwww.docker.com

2.2 Docker版本

  • 社區版(Community Edition,CE)
  • 企業版(Enterprise Edition,EE)

2.3支持平臺

  • Linux(CentOS,Debian,Fedora,Oracle Linux,RHEL,SUSE和Ubuntu)
  • Mac
  • Windows

2.4 Linux安裝Docker

2.4.1 Docker文檔

https://docs.docker.com
https://docs.docker.com/install/linux/docker-ce/centos/#set-up-the-repository

2.4.2 安裝Docker

2.4.2.1關閉防火牆

  systemctl stop firewalld
  systemctl disable firewalld

2.4.2.2關閉selinux

vi /etc/selinux/config
SELINUX=disabled    #設置為disabled
reboot  #重啟伺服器
# 查看selinux狀態
[root@localhost ~]# getenforce
Disabled

2.4.2.3安裝所需的包

yum install -y yum-utils   device-mapper-persistent-data   lvm2

2.4.2.4配置yum源

yum-config-manager --add-repo https://download.docker.com/linux/centos/docker-ce.repo

2.4.2.5安裝docker-ce

yum install docker-ce -y

2.4.2.6啟動

systemctl start docker
# 加入開機啟動
systemctl enable docker

2.4.2.7運行hello-world

docker run hello-world

2.4.2.8查看docker版本

[root@localhost ~]# docker info
Containers: 1
 Running: 0
 Paused: 0
 Stopped: 1
Images: 1
Server Version: 18.09.0
Storage Driver: overlay2
 Backing Filesystem: xfs
 Supports d_type: true
 Native Overlay Diff: true
Logging Driver: json-file
Cgroup Driver: cgroupfs
Plugins:
 Volume: local
 Network: bridge host macvlan null overlay
 Log: awslogs fluentd gcplogs gelf journald json-file local logentries splunk syslog
Swarm: inactive
Runtimes: runc
Default Runtime: runc
Init Binary: docker-init
containerd version: c4446665cb9c30056f4998ed953e6d4ff22c7c39
runc version: 4fc53a81fb7c994640722ac585fa9ca548971871
init version: fec3683
Security Options:
 seccomp
  Profile: default
Kernel Version: 3.10.0-862.el7.x86_64
Operating System: CentOS Linux 7 (Core)
OSType: linux
Architecture: x86_64
CPUs: 1
Total Memory: 1.779GiB
Name: localhost.localdomain
ID: JDCF:RJAD:HIZF:ZAGM:EZNS:46YY:I2AM:OKBH:PRCS:AQBB:4DGT:X3RZ
Docker Root Dir: /var/lib/docker
Debug Mode (client): false
Debug Mode (server): false
Registry: https://index.docker.io/v1/
Labels:
Experimental: false
Insecure Registries:
 127.0.0.0/8
Live Restore Enabled: false
Product License: Community Engine




[root@localhost ~]# docker version
Client:
 Version:           18.09.0
 API version:       1.39
 Go version:        go1.10.4
 Git commit:        4d60db4
 Built:             Wed Nov  7 00:48:22 2018
 OS/Arch:           linux/amd64
 Experimental:      false

Server: Docker Engine - Community
 Engine:
  Version:          18.09.0
  API version:      1.39 (minimum version 1.12)
  Go version:       go1.10.4
  Git commit:       4d60db4
  Built:            Wed Nov  7 00:19:08 2018
  OS/Arch:          linux/amd64
  Experimental:     false

2.4.2.9查看運行了哪些docker

[root@localhost ~]# docker run -it nginx    <<== -it前臺運行、再打開一個終端用於查看
[root@localhost ~]# docker ps
CONTAINER ID        IMAGE               COMMAND                  CREATED             STATUS              PORTS               NAMES
336509fd6799        nginx               "nginx -g 'daemon of…"   8 minutes ago       Up 8 minutes        80/tcp              epic_ride

2.4.2.10查看容器信息

[root@localhost ~]# docker inspect 336509fd6799    <<==容器的id,用docker ps查看得到 
[
    {
        "Id": "336509fd679988cf9e22d9fb1157e3bed5695aeb91d8d706b903b4943f33c30d",
        "Created": "2018-11-08T12:30:38.462038658Z",
        "Path": "nginx",
        "Args": [
            "-g",
            "daemon off;"
        ],
        "State": {
            "Status": "running",
            "Running": true,
            "Paused": false,
            "Restarting": false,
            "OOMKilled": false,
            "Dead": false,
            "Pid": 1926,
            "ExitCode": 0,
            "Error": "",
            "StartedAt": "2018-11-08T12:30:38.800291064Z",
            "FinishedAt": "0001-01-01T00:00:00Z"
        },
        "Image": "sha256:62f816a209e6b57dd5fe98c1994fe3ab19ba4e1fee2a5ec6d77f303be4ed90e9",
        "ResolvConfPath": "/var/lib/docker/containers/336509fd679988cf9e22d9fb1157e3bed5695aeb91d8d706b903b4943f33c30d/resolv.conf",
        "HostnamePath": "/var/lib/docker/containers/336509fd679988cf9e22d9fb1157e3bed5695aeb91d8d706b903b4943f33c30d/hostname",
        "HostsPath": "/var/lib/docker/containers/336509fd679988cf9e22d9fb1157e3bed5695aeb91d8d706b903b4943f33c30d/hosts",
        "LogPath": "/var/lib/docker/containers/336509fd679988cf9e22d9fb1157e3bed5695aeb91d8d706b903b4943f33c30d/336509fd679988cf9e22d9fb1157e3bed5695aeb91d8d706b903b4943f33c30d-json.log",
        "Name": "/epic_ride",
        "RestartCount": 0,
        "Driver": "overlay2",
        "Platform": "linux",
        "MountLabel": "",
        "ProcessLabel": "",
        "AppArmorProfile": "",
        "ExecIDs": null,
        "HostConfig": {
            "Binds": null,
            "ContainerIDFile": "",
            "LogConfig": {
                "Type": "json-file",
                "Config": {}
            },
            "NetworkMode": "default",
            "PortBindings": {},
            "RestartPolicy": {
                "Name": "no",
                "MaximumRetryCount": 0
            },
            "AutoRemove": false,
            "VolumeDriver": "",
            "VolumesFrom": null,
            "CapAdd": null,
            "CapDrop": null,
            "Dns": [],
            "DnsOptions": [],
            "DnsSearch": [],
            "ExtraHosts": null,
            "GroupAdd": null,
            "IpcMode": "shareable",
            "Cgroup": "",
            "Links": null,
            "OomScoreAdj": 0,
            "PidMode": "",
            "Privileged": false,
            "PublishAllPorts": false,
            "ReadonlyRootfs": false,
            "SecurityOpt": null,
            "UTSMode": "",
            "UsernsMode": "",
            "ShmSize": 67108864,
            "Runtime": "runc",
            "ConsoleSize": [
                0,
                0
            ],
            "Isolation": "",
            "CpuShares": 0,
            "Memory": 0,
            "NanoCpus": 0,
            "CgroupParent": "",
            "BlkioWeight": 0,
            "BlkioWeightDevice": [],
            "BlkioDeviceReadBps": null,
            "BlkioDeviceWriteBps": null,
            "BlkioDeviceReadIOps": null,
            "BlkioDeviceWriteIOps": null,
            "CpuPeriod": 0,
            "CpuQuota": 0,
            "CpuRealtimePeriod": 0,
            "CpuRealtimeRuntime": 0,
            "CpusetCpus": "",
            "CpusetMems": "",
            "Devices": [],
            "DeviceCgroupRules": null,
            "DiskQuota": 0,
            "KernelMemory": 0,
            "MemoryReservation": 0,
            "MemorySwap": 0,
            "MemorySwappiness": null,
            "OomKillDisable": false,
            "PidsLimit": 0,
            "Ulimits": null,
            "CpuCount": 0,
            "CpuPercent": 0,
            "IOMaximumIOps": 0,
            "IOMaximumBandwidth": 0,
            "MaskedPaths": [
                "/proc/acpi",
                "/proc/kcore",
                "/proc/keys",
                "/proc/latency_stats",
                "/proc/timer_list",
                "/proc/timer_stats",
                "/proc/sched_debug",
                "/proc/scsi",
                "/sys/firmware"
            ],
            "ReadonlyPaths": [
                "/proc/asound",
                "/proc/bus",
                "/proc/fs",
                "/proc/irq",
                "/proc/sys",
                "/proc/sysrq-trigger"
            ]
        },
        "GraphDriver": {
            "Data": {
                "LowerDir": "/var/lib/docker/overlay2/31cc93e4ef8b9da5b5d98bc9a68cfdd8c1ba2a31bf65bcb21754defd68d85c5d-init/diff:/var/lib/docker/overlay2/240731a3ae18beffce7a5053fb4b45c4a93c52c14b2b18e25751bd5ef5bce0b5/diff:/var/lib/docker/overlay2/613cf356b8ebdacffabca1e2f03c02102a19d13df25caef091c10858ec058731/diff:/var/lib/docker/overlay2/82d2821d41013463c69c23a8c1e58a96ab84ae9c6399a181d0b37f0459c8007b/diff",
                "MergedDir": "/var/lib/docker/overlay2/31cc93e4ef8b9da5b5d98bc9a68cfdd8c1ba2a31bf65bcb21754defd68d85c5d/merged",
                "UpperDir": "/var/lib/docker/overlay2/31cc93e4ef8b9da5b5d98bc9a68cfdd8c1ba2a31bf65bcb21754defd68d85c5d/diff",
                "WorkDir": "/var/lib/docker/overlay2/31cc93e4ef8b9da5b5d98bc9a68cfdd8c1ba2a31bf65bcb21754defd68d85c5d/work"
            },
            "Name": "overlay2"
        },
        "Mounts": [],
        "Config": {
            "Hostname": "336509fd6799",
            "Domainname": "",
            "User": "",
            "AttachStdin": true,
            "AttachStdout": true,
            "AttachStderr": true,
            "ExposedPorts": {
                "80/tcp": {}
            },
            "Tty": true,
            "OpenStdin": true,
            "StdinOnce": true,
            "Env": [
                "PATH=/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin",
                "NGINX_VERSION=1.15.6-1~stretch",
                "NJS_VERSION=1.15.6.0.2.5-1~stretch"
            ],
            "Cmd": [
                "nginx",
                "-g",
                "daemon off;"
            ],
            "ArgsEscaped": true,
            "Image": "nginx",
            "Volumes": null,
            "WorkingDir": "",
            "Entrypoint": null,
            "OnBuild": null,
            "Labels": {
                "maintainer": "NGINX Docker Maintainers <[email protected]>"
            },
            "StopSignal": "SIGTERM"
        },
        "NetworkSettings": {
            "Bridge": "",
            "SandboxID": "f98bbeec0b3b1822c8dd90123c99c7e8225470140148e1dc6075d0bf2685d74b",
            "HairpinMode": false,
            "LinkLocalIPv6Address": "",
            "LinkLocalIPv6PrefixLen": 0,
            "Ports": {
                "80/tcp": null
            },
            "SandboxKey": "/var/run/docker/netns/f98bbeec0b3b",
            "SecondaryIPAddresses": null,
            "SecondaryIPv6Addresses": null,
            "EndpointID": "a6b4036fb031698c228b5b2567da7b07df949a960bffbe119645e88a9730cb27",
            "Gateway": "172.17.0.1",
            "GlobalIPv6Address": "",
            "GlobalIPv6PrefixLen": 0,
            "IPAddress": "172.17.0.2",
            "IPPrefixLen": 16,
            "IPv6Gateway": "",
            "MacAddress": "02:42:ac:11:00:02",
            "Networks": {
                "bridge": {
                    "IPAMConfig": null,
                    "Links": null,
                    "Aliases": null,
                    "NetworkID": "8a60ffdd13c42e28bfa9f6431d0264c790781ff8b5238dfc1f3af34c3d36d9ca",
                    "EndpointID": "a6b4036fb031698c228b5b2567da7b07df949a960bffbe119645e88a9730cb27",
                    "Gateway": "172.17.0.1",
                    "IPAddress": "172.17.0.2",
                    "IPPrefixLen": 16,
                    "IPv6Gateway": "",
                    "GlobalIPv6Address": "",
                    "GlobalIPv6PrefixLen": 0,
                    "MacAddress": "02:42:ac:11:00:02",
                    "DriverOpts": null
                }
            }
        }
    }
]


[root@localhost ~]# curl -I 172.17.0.2
HTTP/1.1 200 OK
Server: nginx/1.15.6
Date: Thu, 08 Nov 2018 12:43:20 GMT
Content-Type: text/html
Content-Length: 612
Last-Modified: Tue, 06 Nov 2018 13:32:09 GMT
Connection: keep-alive
ETag: "5be197d9-264"
Accept-Ranges: bytes

2.4.2.11進入容器中

[root@localhost ~]# docker exec -it 336509fd6799 bash
root@336509fd6799:/# ls
bin  boot  dev  etc  home  lib  lib64  media  mnt  opt  proc  root  run  sbin  srv  sys  tmp  usr  var
root@336509fd6799:/# exit
exit

三、鏡像管理

3.1 鏡像是什麼

  • 一個分層存儲的文件
  • 一個軟體的環境
  • 一個鏡像可以創建N個容器
  • 一種標準化的交付
  • 一個不包含Linux內核而又精簡的Linux操作系統

鏡像不是一個單一的文件,而是有多層構成。我們可以通過docker history 查看鏡像中各層內容及大小,每層對應著Dockerfile中的一條指令。Docker鏡像預設存儲在/var/lib/docker/<storage-driver>中。

[root@localhost ~]# docker history nginx        <<== 查看鏡像有哪些分層
IMAGE               CREATED             CREATED BY                                      SIZE                COMMENT
62f816a209e6        37 hours ago        /bin/sh -c #(nop)  CMD ["nginx" "-g" "daemon…   0B
<missing>           37 hours ago        /bin/sh -c #(nop)  STOPSIGNAL [SIGTERM]         0B
<missing>           37 hours ago        /bin/sh -c #(nop)  EXPOSE 80/tcp                0B
<missing>           37 hours ago        /bin/sh -c ln -sf /dev/stdout /var/log/nginx…   22B
<missing>           37 hours ago        /bin/sh -c set -x  && apt-get update  && apt…   53.8MB
<missing>           37 hours ago        /bin/sh -c #(nop)  ENV NJS_VERSION=1.15.6.0.…   0B
<missing>           37 hours ago        /bin/sh -c #(nop)  ENV NGINX_VERSION=1.15.6-…   0B
<missing>           3 weeks ago         /bin/sh -c #(nop)  LABEL maintainer=NGINX Do…   0B
<missing>           3 weeks ago         /bin/sh -c #(nop)  CMD ["bash"]                 0B
<missing>           3 weeks ago         /bin/sh -c #(nop) ADD file:f8f26d117bc4a9289…   55.3MB


[root@localhost ~]# cd /var/lib/docker/
[root@localhost docker]# ls
builder  buildkit  containerd  containers  image  network  overlay2  plugins  runtimes  swarm  tmp  trust  volumes
[root@localhost docker]# cd overlay2/
[root@localhost overlay2]# ls
240731a3ae18beffce7a5053fb4b45c4a93c52c14b2b18e25751bd5ef5bce0b5
31cc93e4ef8b9da5b5d98bc9a68cfdd8c1ba2a31bf65bcb21754defd68d85c5d
31cc93e4ef8b9da5b5d98bc9a68cfdd8c1ba2a31bf65bcb21754defd68d85c5d-init
613cf356b8ebdacffabca1e2f03c02102a19d13df25caef091c10858ec058731
802c4abe1551fbbba1e4445b149852e2b0a8eb969adc2a45955d60ea88cdd370
82d2821d41013463c69c23a8c1e58a96ab84ae9c6399a181d0b37f0459c8007b
b5044ef06828dd2656c0d59f03cd854917033fe8ebd2e26bc3332b359cfcc148
b5044ef06828dd2656c0d59f03cd854917033fe8ebd2e26bc3332b359cfcc148-init
backingFsBlockDev
l

3.1.1 鏡像從那裡來?

Docker Hub是由Docker公司負責維護的公共註冊中心,包含大量的容器鏡像,Docker工具預設從這個公共鏡像庫下載鏡像。地址:https://hub.docker.com/explore

3.1.2 配置鏡像加速器

https://www.daocloud.io/mirror
curl -sSL https://get.daocloud.io/daotools/set_mirror.sh | sh -s http://f1361db2.m.daocloud.io
systemctl restart docker

3.2 鏡像與容器聯繫

如圖,容器其實是在鏡像的最上面加了一層讀寫層,在運行容器里文件改動時,會先從鏡像裡面要寫的文件複製到容器自己的文件系統中(讀寫層)。

如果容器刪除了,最上面的讀寫層也就被刪除了,改動也就丟失了。所以無論多少個容器共用一個鏡像,所做的寫操作都是從鏡像的文件系統中複製過來操作的,並不會修改鏡像的源文件,這種方式提高磁碟利用率。

若想持久化這些改動,可以通過docker commit將容器保存成一新的鏡像。

root@localhost ~]# docker run -itd nginx
5ba9e0be87ade5e68481bface386c8ef592bb80bbe7bf28cf1572e832c8ce355

[root@localhost ~]# docker ps
CONTAINER ID        IMAGE               COMMAND                  CREATED             STATUS              PORTS               NAMES
5ba9e0be87ad        nginx               "nginx -g 'daemon of…"   51 seconds ago      Up 50 seconds       80/tcp              sharp_mayer
[root@localhost ~]# docker exec -it 5ba9e0be87ad bash
root@5ba9e0be87ad:/# ls
bin  boot  dev  etc  home  lib  lib64  media  mnt  opt  proc  root  run  sbin  srv  sys  tmp  usr  var
root@5ba9e0be87ad:/# touch nginx.txt
root@5ba9e0be87ad:/# exit
exit
[root@localhost ~]# docker inspect 5ba9e0be87ad
....
# 存儲驅動
GraphDriver": {
            "Data": {
                "LowerDir": "/var/lib/docker/overlay2/44cfba513bee96fa98dd85ef9cbf8a88f8286c90291b498a615be6f590bda66a-init/diff:/var/lib/docker/overlay2/240731a3ae18beffce7a5053fb4b45c4a93c52c14b2b18e25751bd5ef5bce0b5/diff:/var/lib/docker/overlay2/613cf356b8ebdacffabca1e2f03c02102a19d13df25caef091c10858ec058731/diff:/var/lib/docker/overlay2/82d2821d41013463c69c23a8c1e58a96ab84ae9c6399a181d0b37f0459c8007b/diff",
                "MergedDir": "/var/lib/docker/overlay2/44cfba513bee96fa98dd85ef9cbf8a88f8286c90291b498a615be6f590bda66a/merged",
                "UpperDir": "/var/lib/docker/overlay2/44cfba513bee96fa98dd85ef9cbf8a88f8286c90291b498a615be6f590bda66a/diff",
                "WorkDir": "/var/lib/docker/overlay2/44cfba513bee96fa98dd85ef9cbf8a88f8286c90291b498a615be6f590bda66a/work"
            },
            "Name": "overlay2"
        },
       ...


[root@localhost ~]# cd /var/lib/docker/overlay2/44cfba513bee96fa98dd85ef9cbf8a88f8286c90291b498a615be6f590bda66a
[root@localhost 44cfba513bee96fa98dd85ef9cbf8a88f8286c90291b498a615be6f590bda66a]# ls
diff  link  lower  merged  work
[root@localhost 44cfba513bee96fa98dd85ef9cbf8a88f8286c90291b498a615be6f590bda66a]# ls diff/         # 與驚喜差異
nginx.txt  root  run  var
[root@localhost 44cfba513bee96fa98dd85ef9cbf8a88f8286c90291b498a615be6f590bda66a]# ls merged/   <<==Nginx工作的數據驅動存儲
bin  boot  dev  etc  home  lib  lib64  media  mnt  nginx.txt  opt  proc  root  run  sbin  srv  sys  tmp  usr  var
[root@localhost 44cfba513bee96fa98dd85ef9cbf8a88f8286c90291b498a615be6f590bda66a]# ls work/
work

3.3 管理鏡像常用命令

docker image --help

指令 描述
ls 列出鏡像
build 構建鏡像來自Dockerfile
history 查看鏡像歷史
inspect 顯示一個或多個鏡像詳細信息
pull 推送一個鏡像到鏡像倉庫
rm 移除一個或多個鏡像
prune 移除未使用的鏡像。沒有被標記或被任何容器引用的。
tag 創建一個引用源鏡像標記目標鏡像
export 導出容器文件系統到tar歸檔文件
import 導入容器文件系統tar歸檔創建鏡像
save 保存一個或多個鏡像到tar歸檔文件
load 載入鏡像來自tar歸檔或標準輸入

四、容器管理

4.1 創建容器常用選項

docker container run --help

選項 描述
-i,-interactive 互動式
-t,-tty 分配一個偽終端
-d,-detach 運行容器到後臺
-e,-env 設置環境變數
-p,-publish list 發佈容器埠到主機
-P,-publish-all 發佈容器所有EXPOSE埠到宿主機隨機埠
-name string 指定容器名稱
-h,-hostname 設置容器主機名
-ip string 指定容器IP,只能用於自定義網路
-network 連接容器到一個網路
-mount mount 將文件系統附加到容器
-v,-volume list 綁定掛載一個捲
-restart string 容器退出時重啟策略,預設no,可選值:[always|on-failure]

4.2 容器資源限制

選項 描述
-m,-memory 容器可以使用的最大記憶體量
-memory-swap 允許交換磁碟的記憶體量
-memory-swappiness=<0-100> 容器使用SWAP分區交換的百分比(0-100,預設為-1)
-oom-kill-disable 禁用OOM Killer
-cpus 可以使用的CPU數量
-cpuset-cpus 限制容器使用特定的CPU核心,(0-3,0,1)
-cpu-shares CPU共用(相對權重)

示例:

4.2.1 記憶體限額

允許容器最多使用500M記憶體和100M的swap,並禁用OOM Killer:
# 允許使用的swap=memory-swap - memory
# memory-swap='-1'時,無限制使用swap
# memory-swap 不設置時,預設swap的值時memory的2倍
# memory-swap的值等於memory值時,禁用swap
docker run -d --name Nginx01 --memory="500m" --memory-swap="600M" --oom-kill-disable nginx

4.2.2 CPU限額

允許容器最多使用一個半的CPU:

docker run -d --name nginx04 --cpus="1.5" nginx

允許容器最多使用50%的CPU:

docker run -d --name nginx05 --cpus='.5' nginx

4.3 管理容器常用命令

docker container --help

選項 描述
ls 列出容器
inspect 查看一個或多個容器詳細信息
commit 創建一個新鏡像來自一個容器
cp 拷貝文件/文件夾到一個容器
logs 獲取一個容器日誌
port 列出或指定容器埠映射
top 顯示一個容器運行的進程
stats 顯示容器資源使用統計
stop/start 停止/啟動一個或多個容器
rm 刪除一個或多個容器

五、管理應用程式數據

5.1 將宿主機數據掛載到容器中的三種方式

Docker提供三種方式數據從宿主機掛載到容器中:

  • Volumes:Docker管理宿主機文件系統的一部分(/var/lib/docker/volumes)。保存數據的最佳方式。
  • bind mounts:將宿主機上的任意位置的文件或者目錄掛載到容器中。
  • tmpfs:掛載存儲在主機系統的記憶體中,而不會寫入主機的文件系統。如果不希望將數據持久化存儲到任何位置,可以使用tmpfs,同時避免寫入容器可寫層提高性能。

5.2 Volume

  • 管理捲
docker volume create nginx-vol
docker volume ls
docker volume inspect nginx-vol
  • 用捲創建一個容器
# 新語法
docker run -d --name=nginx-test --mount src=nginx-vol,dst=/usr/share/nginx/html nginx
# 舊語法
docker run -d --name=nginx-test -v nginx-vol:/usr/share/nginx/html nginx
  • 清理
docker stop nginx-test
docker rm nginx-test
docker volume rm nginx-vol

註意:

1. 如果沒有指定捲,自動創建。
2. 建議使用—mount,更通用。

https://docs.docker.com/engine/admin/volumes/volumes/#start-a-container-with-a-volume

5.3 Bind Mounts

  • 用捲創建一個容器
# 新語法
docker run -d --name=nginx-test --mount type=bind,src=/app/wwwroot,dst=/usr/share/nginx/html nginx
# 舊語法
docker run -d --name=nginx-test -v /app/wwwroot:/usr/share/nginx/html nginx
  • 驗證綁定
docker inspect nginx-test
  • 清理
docker stop nginx-test
docker rm nginx-test

註意:

1.2 如果源文件/目錄沒有存在,不會自動創建,會拋出一個錯誤。

1.3 如果掛載目標在容器中非空目錄,則該目錄現有內容將被隱藏。

https://docs.docker.com/engine/admin/volumes/bind-mounts/#start-a-container-with-a-bind-mount

Volume特點

  • 多個運行容器之間共用數據。
  • 當容器停止或悲移除時,該捲依然存在。
  • 多個容器可以同時掛載相同的捲。
  • 當明確刪除捲時,捲才會被刪除。
  • 將容器的數據存儲在遠程主機或其他存儲上
  • 將數據從一臺Docker主機遷移到另一臺時,先停止容器,然後備份捲的目錄(/var/lib/docker/volumes)

Bind Mounts特點

  • 從主機共用配置文件到容器。預設情況下,掛載主機/etc/resolv.conf到每個容器,提供DNS解析。
  • 在Docker主機上的開發環境和容器之間共用源代碼。例如,可以將Maven target目錄掛載到容器中,每次在Docker主機上構建Maven項目時,容器都可以訪問構建的項目包。
  • 當Docker主機的文件或目錄結構保證與容器所需的綁定掛載一致時。

六、容器網路

6.1 Docker四種網路模式

  • bridge
-net=bridge
預設網路,Docker啟動後創建一個docker0網橋,預設創建的容器也是添加到這個網橋中。
  • host
-net=host
容器不會獲得一個獨立的network namespace,而是與宿主機共用一個,這就意味著容器不會有自己的網卡信息,而是使用宿主機的。容器除了網路,其他都是隔離的。
  • none
-net=none
獲取獨立的network namespave,但不為容器進行任何網路配置,需要我們手動配置。
  • container
-net=container:Name/ID
與指定的容器使用同一個network namespace,具有同樣的網路配置信息,兩個容器除了網路,其他都還黑隔離的。
  • 自定義網路
與預設的bridge原理一樣,但自定義網路具備內部DNS發現,可以通過容器名或者主機名容器之間網路通信。

6.2 容器網路訪問原理

Linux IP信息包過濾原理:

Docker主要通過netfilter/iptables實現網路通信。
iptables由netfilter和iptables組成,netfilter組件是Linux內核集成的信息包過濾系統,它維護一個信息包過濾表,這個表用於控制信息包過濾處理的規則集,而iptables只是一個在用戶空間的工具,用於增刪改查這個過濾表的規則。

filter(過濾) INPUT、OUTPUT、FORWARD
nat(地址轉換) PREROUTING、POSTROUTING、OUTPUT
mangle(拆包、修改、封裝) INPUT、OUTPUT、PREROUTING、 POSTROUTING、OUTPUT
raw(數據包狀態跟蹤) PREROUTING、OUTPUT

 容器訪問外部

# iptables -t nat -nL
Chain POSTROUTING (policy ACCEPT) target prot opt source MASQUERADE all -- 172.17.0.0/16
 destination
0.0.0.0/0

 外部訪問容器

Chain DOCKER (2 references) target prot opt source DNAT tcp -- 0.0.0.0/0
destination
0.0.0.0/0
tcp dpt:88 to:172.18.0.2:80

6.3 橋接宿主機網路與配置固定IP

  • 臨時生效
# 網橋名稱
br_name=br0
# 添加網橋
brctl addbr $br_name
# 給網橋設置IP
ip addr add 192.168.1.120/24 dev $br_name
# 刪除已存在的eth0網卡配置
ip addr del 192.168.1.120/24 dev eth0
# 激活網卡
ip link set $br_name up
# 添加eth0到網橋
brctl addif $br_name eth0
# 添加路由
ip route add default via 192.168.1.1 dev br0

還需要在Docker啟動時橋街這個網橋:
# vi /usr/lib/systemd/system/docker.service
ExecStart=/usr/bin/dockerd -b=br0
# systemctl restart docker
  • 永久生效
# vi /etc/sysconfig/network-scripts/ifcfg-eth0
DEVICE=eth0
TYPE=Ethernet
ONBOOT=yes
BRIDGE=br0

# vi /etc/sysconfig/network-scripts/ifcfg-br0
DEVICE=br0
TYPE=Bridge
ONBOOT=yes
BOOTPROTO=static
IPADDR=192.168.3.10
NETMASK=255.255.255.0
GATEWAY=192.168.3.1
DNS1=114.114.114.114
  • 配置固定IP
C_ID=$(docker run -itd --net=none ubuntu)
C_PID=$(docker inspect -f '{{.State.Pid}}' $C_ID)
# 創建network namespace目錄並將容器的network namespace軟連接到此目錄,以便ip netns命令讀取 mkdir -p /var/run/netns
ln -s /proc/$C_PID/ns/net /var/run/netns/$C_PID
# 添加虛擬網卡veth+容器PID,類型是veth pair,名稱是vp+容器PID
ip link add veth$C_PID type veth peer name vp$C_PID
# 添加虛擬網卡到br0網橋
brctl addif br0 veth$C_PID
# 激活虛擬網卡
ip link set veth$C_PID up
# 設置容器網路信息
IP='192.168.0.123/24'
GW='192.168.0.1'
# 給進程配置一個network namespace
ip link set vp$C_PID netns $C_PID
# 在容器進程裡面設置網卡信息
ip netns exec $C_PID ip link set dev vp$C_PID name eth0
ip netns exec $C_PID ip link set eth0 up
ip netns exec $C_PID ip addr add $IP dev eth0
ip netns exec $C_PID ip route add default via 192.168.1.1
  • pipework工具配置容器固定IP
git clone https://github.com/jpetazzo/pipework.git cp pipework/pipework /usr/local/bin/
docker run -itd --net=none --name test01 ubuntu pipework br0 test01 192.168.0.123/[email protected]

七、Dockerfile

7.1 Dockerfile格式

FROM centos:latest
MAINTAINER huwl
RUN yum install gcc -y
COPY run.sh /usr/bin
EXPOSE 80
CMD ['run.sh]

7.2 Dockerfile常用指令

指令 描述
FROM 構建新鏡像是基於那個鏡像
MAINTAINER 鏡像維護者姓名或郵箱地址
RUN 構建鏡像時運行的Shell命令
COPY 拷貝文件或目錄到鏡像中
ENV 設置環境變數
USER 為RUN、CMD和ENTRPOTIN執行命令指定運行用戶
EXPOSE 聲明容器運行的服務埠
HEALTHCHECK 容器中服務健康檢查
WORKDIR 為RUN、CMD、ENTRYPOTIN、COPY和ADD設置工作目錄
ENTRYPOIN 運行容器時執行,如果有多個ENTRYPOIN指令,最後一個生效
CMD 運行容器時執行,如果有多個CMD指令,最後一個生效

7.3 Build構建鏡像

Usage:docker build [OPTIONS] PATH | URL | - [flags]
Options:
-t, --tag list      # 鏡像名稱
-f,--file string    #指定Dockerfile文件位置


# docker build .
# docker bulid -t shykes/myapp .
# docker bulid -t shykes/myapp -f /path/Dockerfile /path
# docker bulid -t shykes/myapp http://www.example.com/Dockerfile

7.4 企業應用案例

7.4.1 構建Nginx基礎鏡像

  • Dockerfile
FROM centos:7
RUN yum install -y gcc gcc-c++ make openssl-devel pcre-devel dg-devel iproute net-tools telnet wget curl && yum clean all && rm -rf /var/cache/yum/*
RUN wget http://nginx.org/download/nginx-1.15.5.tar.gz && tar zxf nginx-1.15.5.tar.gz && cd nginx-1.15.5 && ./configure --prefix=/usr/local/nginx --with-http_ssl_module --with-http_stub_status_module && make && make install
ENV PATH $PATH:/usr/local/nginx/sbin
WORKDIR /usr/local/nginx
EXPOSE 80
CMD ["./sbin/nginx","-g","daemon off;"]
  • 構建鏡像
docker build -t nginx:v1 -f Dockerfile .
# Successfully built 373a0bdefe50
# Successfully tagged nginx:v1

[root@localhost /]# docker image ls
REPOSITORY          TAG                 IMAGE ID            CREATED             SIZE
nginx               v1                  373a0bdefe50        56 seconds ago      335MB
<none>              <none>              d582c01a839f        4 minutes ago       200MB
nginx               latest              62f816a209e6        2 days ago          109MB
centos              7                   75835a67d134        4 weeks ago         200MB
hello-world         latest              4ab4c602aa5e        2 months ago        1.84kB
  • 啟動測試
[root@localhost /]# docker run -d --name nginx100 -p 80:80 nginx:v1
a29daf4614116f7dba18461e871d1a45ec9b55f722a98bead791c12294b9f1d3
[root@localhost /]# docker ps -l
CONTAINER ID        IMAGE               COMMAND                  CREATED             STATUS              PORTS                NAMES
a29daf461411        nginx:v1            "./sbin/nginx -g 'da…"   6 seconds ago       Up 5 seconds        0.0.0.0:80->80/tcp   nginx100


[root@localhost /]# curl -I http://192.168.56.146/
HTTP/1.1 200 OK
Server: nginx/1.15.5
Date: Fri, 09 Nov 2018 12:34:03 GMT
Content-Type: text/html
Content-Length: 612
Last-Modified: Fri, 09 Nov 2018 12:29:20 GMT
Connection: keep-alive
ETag: "5be57da0-264"
Accept-Ranges: bytes

7.4.2 構建PHP基礎鏡像

  • dockerfile
FROM centos:7
RUN yum install -y gcc gcc-c++ make gd-devel libxml2-devel libcurl-devel libjpeg-devel libpng-devel openssl-devel
ADD php-5.6.31.tar.gz /tmp/

RUN cd /tmp/php-5.6.31 && \
    ./configure --prefix=/usr/local/php \
    --with-config-file-path=/usr/local/php/etc \
    --with-mysql --with-mysqli \
    --with-openssl --with-zlib --with-curl --with-gd \
    --with-jpeg-dir --with-png-dir --with-iconv \
    --enable-fpm --enable-zip --enable-mbstring && \
    make -j 4 && \
    make install && \
    cp /usr/local/php/etc/php-fpm.conf.default /usr/local/php/etc/php-fpm.conf && \
    sed -i "s/127.0.0.1/0.0.0.0/" /usr/local/php/etc/php-fpm.conf && \
    sed -i "21a \daemonize = no" /usr/local/php/etc/php-fpm.conf
COPY php.ini /usr/local/php/etc

RUN rm -rf /tmp/php-5.6.31* && yum clean all

WORKDIR /usr/local/php
EXPOSE 9000
CMD ["./sbin/php-fpm", "-c", "/usr/local/php/etc/php-fpm.conf"]
  • 構建php鏡像
docker build -t php:v1 -f dockerfile .
  • 啟動測試
[root@localhost php]# docker run -d --name php01 php:v1
ed5276251a6bf5124efba4b314d29a2dbfd12ddc0e0c3371ea16184a07c12bbc
[root@localhost php]# docker ps -l
CONTAINER ID        IMAGE               COMMAND                  CREATED             STATUS              PORTS               NAMES
ed5276251a6b        php:v1              "./sbin/php-fpm -c /…"   5 seconds ago       Up 4 seconds        9000/tcp            php01
[root@localhost php]# docker exec -it php01 bash
[root@ed5276251a6b php]# ls
bin  etc  include  lib  php  sbin  var
[root@ed5276251a6b php]# sbin/php-fpm -v
PHP 5.6.31 (fpm-fcgi) (built: Nov 10 2018 01:10:28)
Copyright (c) 1997-2016 The PHP Group
Zend Engine v2.6.0, Copyright (c) 1998-2016 Zend Technologies

7.4.3 構建Tomcat基礎鏡像並項目測試

  • dockerfile
FROM centos:7

ADD jdk-8u45-linux-x64.tar.gz /usr/local
ENV JAVA_HOME /usr/local/jdk1.8.0_45

ADD apache-tomcat-8.0.46.tar.gz /usr/local
COPY server.xml /usr/local/apache-tomcat-8.0.46/conf

RUN rm -f /usr/local/*.tar.gz

WORKDIR /usr/local/apache-tomcat-8.0.46
EXPOSE 8080
ENTRYPOINT ["./bin/catalina.sh", "run"]
  • 構建Tomcat鏡像
docker build -t tomcat:v1 -f Dockerfile .
  • 啟動測試
[root@localhost tomcat]# docker run -d --name tomcat01 -p 8080:8080 tomcat:v1
b9ba85bc64748c90ebe8df19e41c36490881cbcf174dab00d127ae6bf1141814
[root@localhost tomcat]# curl -I http://192.168.56.146:8080
HTTP/1.1 200 OK
Server: Apache-Coyote/1.1
Content-Type: text/html;charset=UTF-8
Transfer-Encoding: chunked
Date: Sat, 10 Nov 2018 01:26:59 GMT

7.5.1 快速部署LNMP網站平臺

  • 創建自定義網路
docker network create lnmp
  • 創建MySQL容器
docker run -d --name lnmp_mysql --net lnmp --mount src=mysql-vol,dst=/var/lib/mysql -e MYSQL_ROOT_PASSWORD=123456 -e MYSQL_DATABASE=wordpress mysql:5.7 --character-set-server=utf8
  • 創建PHP容器
docker run -d --name lnmp_php --net lnmp --mount src=wwwroot,dst=/wwwwroot php:v1
  • 創建Nginx容器
docker run -d --name lnmp_nginx --net lnmp -p 80:80 --mount type=bind,src=$(pwd)/nginx.conf,dst=/usr/local/nginx/conf/nginx.conf --mount src=wwwroot,dst=/wwwroot nginx:v1
  • 以wordpress博客為例
https://cn.wordpress.org/wordpress-4.9.4-zh_CN.tar.gz

八、企業級鏡像倉庫Harbor

8.1 Harbor介紹

​ Habor是由VMWare公司開源的容器鏡像倉庫。事實上,Habor是在Docker Registry上進行了相應的企業級擴展,從而獲得了更加廣泛的應用,這些新的企業級特性包括:管理用戶界面,基於角色的訪問控制,AD/DALP集成以及審計日誌等,足以滿足基本企業需求。

官方地址:https://vmware.github.io/harbor/cn/

組件 功能
harbor-adminserver 配置管理中心
harbor-db MySQL資料庫
harbor-jobservice 負責鏡像複製
harbor-log 記錄操作日誌
harbor-ui web管理頁面和API
Nginx 前端代理,負責前端頁面和鏡像上傳或下載轉發
reids 會話
registry 鏡像存儲

8.2 Harbor部署

Harbor安裝有3種方式:

  • 線上安裝:從Docker Hub下載Harbor相關鏡像,因此安裝軟體包非常小
  • 離線安裝:安裝包包含部署的相關鏡像,因此安裝包比較大
  • OVA安裝程式:當用戶具有vCenter環境時,使用此安裝程式,在部署OVA後啟動Harbor

離線安裝下載地址:https://github.com/goharbor/harbor/releases

  • 部署
curl -L "https://github.com/docker/compose/releases/download/1.22.0/docker-compose-$(uname -s)-$(uname -m)" -o /usr/local/bin/docker-compose
chmod +x /usr/local/bin/docker-compose

tar xf harbor-offline-installer-v1.6.1.tgz
cd harbor
vim harbor.cfg
harbor_admin_password = Harbor12345

./prepare
./install.sh

[root@localhost harbor]# docker-compose ps
       Name                     Command                  State                                    Ports
-------------------------------------------------------------------------------------------------------------------------------------
harbor-adminserver   /harbor/start.sh                 Up (healthy)
harbor-db            /entrypoint.sh postgres          Up (healthy)   5432/tcp
harbor-jobservice    /harbor/start.sh                 Up
harbor-log           /bin/sh -c /usr/local/bin/ ...   Up (healthy)   127.0.0.1:1514->10514/tcp
harbor-ui            /harbor/start.sh                 Up (healthy)
nginx                nginx -g daemon off;             Up (healthy)   0.0.0.0:443->443/tcp, 0.0.0.0:4443->4443/tcp, 0.0.0.0:80->80/tcp
redis                docker-entrypoint.sh redis ...   Up             6379/tcp
registry             /entrypoint.sh /etc/regist ...   Up (healthy)   5000/tcp
  • 訪問

http://192.168.56.146/harbor/sign-in

8.3 Harbor基礎使用

  • 預設上傳鏡像連接使用https,添加http受信任
[root@localhost harbor]# cat /etc/docker/daemon.json
{
"registry-mirrors": ["http://f1361db2.m.daocloud.io"],
"insecure-registries": ["192.168.56.146"]       #<<= 加入harbor的地址

}
  • 重啟docker
systemctl restart docker

在Harbor web管理——“系統管理”——“用戶管理”——新建用戶,在——“項目”——“library倉庫” ——“成員”把之前添加的用戶進來並賦予許可權

  • 登錄倉庫上傳鏡像
docker tag nginx:v1 192.168.56.146/library/nginx:v1
docker login harbor地址
docker push 192.168.56.146/library/nginx:v1

九、圖形化界面管理

9.1 Portainer

官網:https://portainer.io

https://portainer.io/install.html

Portainer是一個開源、輕量級Docker管理用戶界面,基於Docker API,可管理Docker主機或Swarm集群,支持最新版Docker和Swarm模塊。

  • 創建捲
docker volume create portainer_data
  • 創建Portainer容器
docker run -d -p 9000:9000 -v /var/run/docker.sock:/var/run/docker.sock -v portainer_data:/data portainer/portainer
  • 訪問portainer

http://192.168.56.146:9000

十、構建容器監控系統

10.1 cAdvisor+InfluxDB+Grafna

  • 創建monitor
docker network create monitor
  • Influxdb
docker run -d --name influxdb --net monitor -p 8083:8083 -p 8086:8086 tutum/influxdb
  • cAdvisor
docker run -d --name=cadvisor --net monitor -p 8081:8080 --mount type=bind,src=/,dst=/rootfs,ro --mount type=bind,src=/var/run,dst=/var/run --mount type=bind,src=/sys,dst=/sys,ro --mount type=bind,src=/var/lib/docker/,dst=/var/lib/docker,ro google/cadvisor -storage_driver=influxdb -storage_driver_db=cadvisor -storage_driver_host=influxdb:8086
  • Grafana
docker run -d --name grafana --net monitor -p 3000:3000 grafana/grafana

您的分享是我們最大的動力!

-Advertisement-
Play Games
更多相關文章
  • 1.CC為文本控制項的父類,它繼承為control,所以他是控制項, 2.CP繼承FrameworkElement,所以他是容器,相當於占位符 3.想讓控制項中能包含子控制項就需要用CP,反之用CC就行。(不太嚴謹) 在控制項的Template 屬性中 定義樣式一般會用CP 4.使用它們可以做到控制項無限擴展 ...
  • whereis 查找命令的位置,包括執行文件、源代碼、手冊文件。 此命令的適用範圍:RedHat、RHEL、Ubuntu、CentOS、SUSE、openSUSE、Fedora。 1、語法 whereis [選項] cmd whereis [-bmsu] [-BMS directory... -f] ...
  • 、什麼是運維?什麼是游戲運維? 1)運維是指大型組織已經建立好的網路軟硬體的維護,就是要保證業務的上線與運作的正常, 在他運轉的過程中,對他進行維護,他集合了網路、系統、資料庫、開發、安全、監控於一身的技術 運維又包括很多種,有DBA運維、網站運維、虛擬化運維、監控運維、游戲運維等等 2)游戲運維又 ...
  • 今天運營同事給我說在用ueditor編寫文章的時候上傳圖片報錯,錯誤信息為 , 翻譯過來就是請求實體太大,這是因為伺服器(我們的伺服器是Nginx)對上傳的文件大小是有限制的,我們修改Nginx的配置文件把允許上傳的文件大小配置大一些即可,在nginx.conf的http模塊增加 這是我把上傳文件的 ...
  • 測試 有點點激動 ...
  • ifconfig command not found 請先檢查機器是不是可以聯網,下麵的方法僅適用於可以聯網的機器 輸入ip addr確認ip地址時候設置正常,設置好的如下圖所示,如果沒有獲取到則自己進行設置 檢查sbin目錄是不是存在,直接cd就行 確認ifconfig是不是安裝, 打開 cd /... ...
  • 1. 如何創建一個定時任務,通過systemd系統 <! TOC "1. 如何創建一個定時任務,通過systemd系統" "1.1. systemd中的timer" "1.2. 自定義定時任務" "1.2.1. 具體步驟" "1.2.2. [Timer]區塊屬性詳情" "1.3. 刪除定時器" <! ...
  • 1..配置日誌文件路徑 命令:pm2 start /home/admin/node/fotonIp/bin/www --name ip -i 4 -o "/app/node/logs/out.log" -e "/app/node/logs/err.log" 2. 利用 pm2_logrotate 來 ...
一周排行
    -Advertisement-
    Play Games
  • 移動開發(一):使用.NET MAUI開發第一個安卓APP 對於工作多年的C#程式員來說,近來想嘗試開發一款安卓APP,考慮了很久最終選擇使用.NET MAUI這個微軟官方的框架來嘗試體驗開發安卓APP,畢竟是使用Visual Studio開發工具,使用起來也比較的順手,結合微軟官方的教程進行了安卓 ...
  • 前言 QuestPDF 是一個開源 .NET 庫,用於生成 PDF 文檔。使用了C# Fluent API方式可簡化開發、減少錯誤並提高工作效率。利用它可以輕鬆生成 PDF 報告、發票、導出文件等。 項目介紹 QuestPDF 是一個革命性的開源 .NET 庫,它徹底改變了我們生成 PDF 文檔的方 ...
  • 項目地址 項目後端地址: https://github.com/ZyPLJ/ZYTteeHole 項目前端頁面地址: ZyPLJ/TreeHoleVue (github.com) https://github.com/ZyPLJ/TreeHoleVue 目前項目測試訪問地址: http://tree ...
  • 話不多說,直接開乾 一.下載 1.官方鏈接下載: https://www.microsoft.com/zh-cn/sql-server/sql-server-downloads 2.在下載目錄中找到下麵這個小的安裝包 SQL2022-SSEI-Dev.exe,運行開始下載SQL server; 二. ...
  • 前言 隨著物聯網(IoT)技術的迅猛發展,MQTT(消息隊列遙測傳輸)協議憑藉其輕量級和高效性,已成為眾多物聯網應用的首選通信標準。 MQTTnet 作為一個高性能的 .NET 開源庫,為 .NET 平臺上的 MQTT 客戶端與伺服器開發提供了強大的支持。 本文將全面介紹 MQTTnet 的核心功能 ...
  • Serilog支持多種接收器用於日誌存儲,增強器用於添加屬性,LogContext管理動態屬性,支持多種輸出格式包括純文本、JSON及ExpressionTemplate。還提供了自定義格式化選項,適用於不同需求。 ...
  • 目錄簡介獲取 HTML 文檔解析 HTML 文檔測試參考文章 簡介 動態內容網站使用 JavaScript 腳本動態檢索和渲染數據,爬取信息時需要模擬瀏覽器行為,否則獲取到的源碼基本是空的。 本文使用的爬取步驟如下: 使用 Selenium 獲取渲染後的 HTML 文檔 使用 HtmlAgility ...
  • 1.前言 什麼是熱更新 游戲或者軟體更新時,無需重新下載客戶端進行安裝,而是在應用程式啟動的情況下,在內部進行資源或者代碼更新 Unity目前常用熱更新解決方案 HybridCLR,Xlua,ILRuntime等 Unity目前常用資源管理解決方案 AssetBundles,Addressable, ...
  • 本文章主要是在C# ASP.NET Core Web API框架實現向手機發送驗證碼簡訊功能。這裡我選擇是一個互億無線簡訊驗證碼平臺,其實像阿裡雲,騰訊雲上面也可以。 首先我們先去 互億無線 https://www.ihuyi.com/api/sms.html 去註冊一個賬號 註冊完成賬號後,它會送 ...
  • 通過以下方式可以高效,並保證數據同步的可靠性 1.API設計 使用RESTful設計,確保API端點明確,並使用適當的HTTP方法(如POST用於創建,PUT用於更新)。 設計清晰的請求和響應模型,以確保客戶端能夠理解預期格式。 2.數據驗證 在伺服器端進行嚴格的數據驗證,確保接收到的數據符合預期格 ...