linux进程问题排查方法
linux进程突然挂了,怎么找原因
- 查看日志,systemctl status
- 检查网络情况
- top检查内存等信息情况,看看是不是oom
- dmesg查看内核信息
- lsblk,查看是不是硬件挂了
暂时就想到这么多
linux进程突然挂了,怎么找原因
暂时就想到这么多
虚拟机:
基础设施(Infrastructure)。它可以是你的个人电脑,数据中心的服务器,或者是云主机。
主操作系统(Host Operating System)。你的个人电脑之上,运行的可能是MacOS,Windows或者某个Linux发行版。
虚拟机管理系统(Hypervisor)。利用Hypervisor,可以在主操作系统之上运行多个不同的从操作系统。类型1的Hypervisor有支持MacOS的HyperKit,支持Windows的Hyper-V以及支持Linux的KVM。类型2的Hypervisor有VirtualBox和VMWare。
从操作系统(Guest Operating System)。假设你需要运行3个相互隔离的应用,则需要使用Hypervisor启动3个从操作系统,也就是3个虚拟机。这些虚拟机都非常大,也许有700MB,这就意味着它们将占用2.1GB的磁盘空间。更糟糕的是,它们还会消耗很多CPU和内存。
各种依赖。每一个从操作系统都需要安装许多依赖。如果你的的应用需要连接PostgreSQL的话,则需要安装libpq-dev;如果你使用Ruby的话,应该需要安装gems;如果使用其他编程语言,比如Python或者Node.js,都会需要安装对应的依赖库。
应用。安装依赖之后,就可以在各个从操作系统分别运行应用了,这样各个应用就是相互隔离的。
docker:
主操作系统(Host Operating System)。所有主流的Linux发行版都可以运行Docker。对于MacOS和Windows,也有一些办法"运行"Docker。
Docker守护进程(Docker Daemon)。Docker守护进程取代了Hypervisor,它是运行在操作系统之上的后台进程,负责管理Docker容器。
各种依赖。对于Docker,应用的所有依赖都打包在Docker镜像中,Docker容器是基于Docker镜像创建的。
应用。应用的源代码与它的依赖都打包在Docker镜像中,不同的应用需要不同的Docker镜像。不同的应用运行在不同的Docker容器中,它们是相互隔离的。
区别:
虚拟机实现资源的隔离的方式是利用独立的Guest OS,以及利用Hypervisor虚拟化CPU、内存、IO等设备来实现的,Docker不需要Hypervisor实现硬件资源的虚拟化,他利用Namespace 实现了系统环境的隔离,利用了cgroup实现了资源的限制,利用镜像实例实现跟环境的隔离。
namespce是linux的底层概念,在内核层实现,每个docker容器运行在一个docker主进程并且共用一个宿主机内核,各自运行在宿主机的用户空间,彼此之间采用一定的措施互相隔离,以保证自己或宿主机内核不受其他进程的干扰。namespace就是实现隔离的措施。所以运行在Docker容器上的程序,直接使用的都是实际物理机的硬件资源。因此在cpu、内存、利用率上,Docker将会在效率上具有更大的优势。docker启动都是秒级,且兼容性强。
namaspcace一共有6种
每个容器都有独立的文件系统挂载点,在创建了一个新的mount namespace后,进程系统对文件系统的挂在/写在动作就不会影响到别的namespace
实验
#拉取两个centos镜像
[root@server1 ~]# docker run -d centos:7 ping baidu.com
5c101d7baa31692d63c4036b0570fa8a2dab1d9a4884e4ee65a410de2e23b631
[root@server1 ~]# docker run -d centos:7 ping baidu.com
3edc6c7e7ed70cfc9dbc9605636aa68c47afaff5cfce2ff8de4a93e5199ca310
[root@server1 ~]# docker ps
CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES
3edc6c7e7ed7 centos:7 "ping baidu.com" 3 seconds ago Up 2 seconds crazy_galileo
5c101d7baa31 centos:7 "ping baidu.com" 19 seconds ago Up 16 seconds pedantic_moore
登入两个镜像,各自准备一份一模一样的文件
[root@server1 ~]# docker exec -it 3 bash
[root@3edc6c7e7ed7 /]# pwd
/
[root@3edc6c7e7ed7 /]# whoami
root
[root@3edc6c7e7ed7 /]# cd
[root@3edc6c7e7ed7 ~]# ll
total 4
-rw-------. 1 root root 3416 Nov 13 2020 anaconda-ks.cfg
[root@3edc6c7e7ed7 ~]# echo "this is server1" > 123.txt
[root@3edc6c7e7ed7 ~]# ll
total 8
-rw-r--r--. 1 root root 16 Mar 18 03:09 123.txt
-rw-------. 1 root root 3416 Nov 13 2020 anaconda-ks.cfg
[root@3edc6c7e7ed7 ~]# exit
exit
[root@server1 ~]# docker exec -it 5 bash
[root@5c101d7baa31 /]# cd
[root@5c101d7baa31 ~]# echo "this is server2" > 123.txt
[root@5c101d7baa31 ~]# exit
exit
在宿主机寻找文件,diff存放的是差分文件,merged下存放的是运行时的存储文件,docker使用chroot技术把容器锁定到一个指定的运行目录里
[root@server1 ~]# find / -name "123.txt"
/var/lib/docker/overlay2/c1429f6c6bdeb99d56f1710f29a4d705fbaab27f6a7a20e74849cfc5da9fb17e/diff/root/123.txt
/var/lib/docker/overlay2/c1429f6c6bdeb99d56f1710f29a4d705fbaab27f6a7a20e74849cfc5da9fb17e/merged/root/123.txt
/var/lib/docker/overlay2/0ec5a01a65be3e401a09d19d5684c73636738914311a98c126c391bfc6256b49/diff/root/123.txt
/var/lib/docker/overlay2/0ec5a01a65be3e401a09d19d5684c73636738914311a98c126c391bfc6256b49/merged/root/123.txt
[root@server1 ~]# cat /var/lib/docker/overlay2/c1429f6c6bdeb99d56f1710f29a4d705fbaab27f6a7a20e74849cfc5da9fb17e/diff/root/123.txt
this is server2
[root@server1 ~]# cat /var/lib/docker/overlay2/c1429f6c6bdeb99d56f1710f29a4d705fbaab27f6a7a20e74849cfc5da9fb17e/merged/root/123.txt
this is server2
[root@server1 ~]# cat /var/lib/docker/overlay2/0ec5a01a65be3e401a09d19d5684c73636738914311a98c126c391bfc6256b49/diff/root/123.txt
this is server1
[root@server1 ~]# cat /var/lib/docker/overlay2/0ec5a01a65be3e401a09d19d5684c73636738914311a98c126c391bfc6256b49/merged/root/123.txt
this is server1
IPC隔离的是进程间的通信,其会用标识符表示不同的消息队列,进程间通过找到标识符对应的消息队列来完成通信,IPC namespace做的事情就是相同的标识符在不同namespace上对应不同的消息队列,这样不同namespace的进程无法完成进程间通信。
UTS Namespace用于对主机名和域名进行隔离,它使得一个容器拥有属于自己hostname标识,这个主机名标识独立于宿主机系统和其上的其他容器。
PID用于隔离进程号,每个容器内部有一个父进程来管理下属进程,当创建一个PID Namespace时,其第一个进程PID号在容器内部会被映射为1,当这个进程不是前台进程的时候容器会直接停止,用docker ps找不到刚开的容器可能是这个原因。你可以在宿主机用pkill或者kill杀死对应容器的containerd-shim进程,相关容器也能被直接杀死
[root@server1 ~]# yum install psmisc.x86_64 -y
[root@server1 ~]# pstree -p
systemd(1)─┬─NetworkManager(6349)─┬─dhclient(6428)
│ ├─{NetworkManager}(6398)
│ └─{NetworkManager}(6400)
├─agetty(6383)
├─auditd(5770)───{auditd}(5771)
├─chronyd(6385)
├─containerd(6660)─┬─{containerd}(6705)
│ ├─{containerd}(6706)
│ ├─{containerd}(6707)
│ ├─{containerd}(6708)
│ ├─{containerd}(6709)
│ ├─{containerd}(6751)
│ ├─{containerd}(6752)
│ └─{containerd}(6754)
├─containerd-shim(7552)─┬─ping(7571)
│ ├─{containerd-shim}(7554)
│ ├─{containerd-shim}(7555)
│ ├─{containerd-shim}(7556)
│ ├─{containerd-shim}(7557)
│ ├─{containerd-shim}(7558)
│ ├─{containerd-shim}(7559)
│ ├─{containerd-shim}(7560)
│ ├─{containerd-shim}(7561)
│ ├─{containerd-shim}(7596)
│ └─{containerd-shim}(7696)
├─containerd-shim(7642)─┬─ping(7663)
│ ├─{containerd-shim}(7643)
│ ├─{containerd-shim}(7644)
│ ├─{containerd-shim}(7645)
│ ├─{containerd-shim}(7646)
│ ├─{containerd-shim}(7647)
│ ├─{containerd-shim}(7648)
│ ├─{containerd-shim}(7649)
│ ├─{containerd-shim}(7651)
│ ├─{containerd-shim}(7683)
│ └─{containerd-shim}(7698)
├─crond(6366)
├─dbus-daemon(6232)───{dbus-daemon}(6348)
├─dockerd(6755)─┬─{dockerd}(6831)
│ ├─{dockerd}(6834)
│ ├─{dockerd}(6835)
│ ├─{dockerd}(6836)
│ ├─{dockerd}(6837)
│ ├─{dockerd}(6915)
│ ├─{dockerd}(6916)
│ ├─{dockerd}(7543)
│ └─{dockerd}(7590)
├─irqbalance(6228)
├─lvmetad(3167)
├─master(6748)─┬─pickup(7426)
│ └─qmgr(6750)
├─polkitd(6350)─┬─{polkitd}(6393)
│ ├─{polkitd}(6394)
│ ├─{polkitd}(6395)
│ ├─{polkitd}(6396)
│ ├─{polkitd}(6397)
│ └─{polkitd}(6402)
├─rsyslogd(6649)─┬─{rsyslogd}(7143)
│ └─{rsyslogd}(7146)
├─sshd(6651)─┬─sshd(7474)───bash(7480)───pstree(9856)
│ └─sshd(7478)───sftp-server(7499)
├─systemd-journal(3148)
├─systemd-logind(6231)
├─systemd-udevd(3185)
└─tuned(6652)─┬─{tuned}(6917)
├─{tuned}(6918)
├─{tuned}(6919)
└─{tuned}(6932)
User用于隔离用户资源,一个进程在namespace里的用户和组id与它在host里的id不一样,一个host的普通用户可以在该容器下拥有root权限,但是他的特权被限定在这个容器内
network用于隔离网络资源,每一个容器都类似于虚拟机一样有自己的网卡、监听端口、TCP/IP协议栈等,Docker使用networknamespace启动一个vethX接口,这样容器将拥有它自己的桥接IP地址,通常是docker0,而docker0实质就是linux的虚拟网桥
https://cr.console.aliyun.com/cn-hangzhou/instances
安装docker-ce和客户端
yum install wget.x86_64 -y
rm -rf /etc/yum.repos.d/*
wget -O /etc/yum.repos.d/Centos-7.repo http://mirrors.aliyun.com/repo/Centos-7.repo
wget -O /etc/yum.repos.d/epel-7.repo http://mirrors.aliyun.com/repo/epel-7.repo
wget -O /etc/yum.repos.d/docker-ce.repo https://mirrors.aliyun.com/docker-ce/linux/centos/docker-ce.repo
yum install docker-ce -y
启动
[root@server1 ~]# systemctl start docker.service
[root@server1 ~]# systemctl enable docker.service
Created symlink from /etc/systemd/system/multi-user.target.wants/docker.service to /usr/lib/systemd/system/docker.service.
快速案例(nginx)
[root@server1 ~]# docker pull nginx #拉取镜像
Using default tag: latest
latest: Pulling from library/nginx
f7a1c6dad281: Pull complete
4d3e1d15534c: Pull complete
9ebb164bd1d8: Pull complete
59baa8b00c3c: Pull complete
a41ae70ab6b4: Pull complete
e3908122b958: Pull complete
Digest: sha256:9ddd8cf6d01f497638130950769e279e0b669cd07d11e2bbc4ffead528c9e6e2
Status: Downloaded newer image for nginx:latest
docker.io/library/nginx:latest
[root@server1 ~]# docker images #查看现有的镜像
REPOSITORY TAG IMAGE ID CREATED SIZE
nginx latest c919045c4c2b 2 weeks ago 142MB
(TAG如不在下载时指定默认为lastest)
[root@server1 ~]# docker run -d -p 80:80 nginx
639cb466a53c05eac9eea4786a446be8504834288988bde30b8e1201306c6a65
# -d后台运行容器并且返回容器ID,-p端口映射
[root@server1 ~]# docker ps #查看当前正在运行的镜像
CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES
#镜像id 使用的镜像 启动容器运行的命令 创建时间 状态 映射 容器名
639cb466a53c nginx "/docker-entrypoint.…" 5 minutes ago Up 5 minutes 0.0.0.0:80->80/tcp, :::80->80/tcp fervent_clarke
[root@server1 ~]# docker exec -it 639cb466a53c bash #进入这个docker并创建个bash
root@639cb466a53c:/#
root@639cb466a53c:/# exit
exit
[root@server1 ~]# curl 192.168.226.148
<!DOCTYPE html>
<html>
<head>
<title>Welcome to nginx!</title>
docker stop
[root@server1 ~]# docker stop 639cb466a53c # 暂停镜像
639cb466a53c
[root@server1 ~]# docker ps
CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES
[root@server1 ~]# docker ps -a #显示全部镜像
CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES
639cb466a53c nginx "/docker-entrypoint.…" 17 minutes ago Exited (0) 29 seconds ago fervent_clarke
[root@server1 ~]# docker rm 639cb466a53c #删除
639cb466a53c
[root@server1 ~]# docker ps -a
CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES
[root@server1 ~]#
docker信息
[root@server1 ~]# docker info
Client:
Context: default
Debug Mode: false
Plugins:
app: Docker App (Docker Inc., v0.9.1-beta3)
buildx: Docker Buildx (Docker Inc., v0.8.0-docker)
scan: Docker Scan (Docker Inc., v0.17.0)
Server:
Containers: 1 #当前容器总数
Running: 0 #运行种
Paused: 0 #暂停
Stopped: 1 #停止
Images: 2 #镜像数
Server Version: 20.10.13 #服务器版本
Storage Driver: overlay2 #存储引擎
Backing Filesystem: xfs #后端文件系统
Supports d_type: true #是否支持d_type
Native Overlay Diff: true #是否支持差异数据存储
userxattr: false
Logging Driver: json-file #日志文件类型
Cgroup Driver: cgroupfs #cgroup类型
Cgroup Version: 1
Plugins:
Volume: local
Network: bridge host ipvlan macvlan null overlay
Log: awslogs fluentd gcplogs gelf journald json-file local logentries splunk syslog
Swarm: inactive
Runtimes: io.containerd.runtime.v1.linux runc io.containerd.runc.v2
Default Runtime: runc #runtime
Init Binary: docker-init #初始化容器的守护进程
containerd version: 2a1d4dbdb2a1030dc5b01e96fb110a9d9f150ecc
runc version: v1.0.3-0-gf46b6ba
init version: de40ad0
Security Options: #安全选项
seccomp
Profile: default
Kernel Version: 3.10.0-957.el7.x86_64 #宿主机内核版本
Operating System: CentOS Linux 7 (Core) #宿主机操作系统
OSType: linux #宿主机操作系统类型
Architecture: x86_64 #宿主机架构
CPUs: 2 #宿主机cpu数量
Total Memory: 972.6MiB #宿主机总内存
Name: server1 #宿主机名
ID: SEVK:M4YS:NEBL:SFRQ:72OS:5JDD:HC6Z:NUMM:7MIC:2B3D:KS3Z:4H4G
Docker Root Dir: /var/lib/docker #宿主机数据保存目录
Debug Mode: false
Registry: https://index.docker.io/v1/ #仓库镜像
Labels:
Experimental: false
Insecure Registries:
127.0.0.0/8
Registry Mirrors:
https://afh2ckya.mirror.aliyuncs.com/ #镜像加速
Live Restore Enabled: false
WARNING: bridge-nf-call-iptables is disabled
WARNING: bridge-nf-call-ip6tables is disabled
docker目前的默认存储引擎为overlay2,不同存储引擎需要相应的系统支持
https://www.cnblogs.com/youruncloud/p/5736718.html
docker search 镜像名 #搜索镜像
docker pull name:tag #下载镜像:描述标签,不写默认latest
[root@server1 ~]# docker images #列出所有镜像
REPOSITORY TAG IMAGE ID CREATED SIZE
nginx latest c919045c4c2b 2 weeks ago 142MB
centos 7 eeb6ee3f44bd 6 months ago 204MB
docker inspect:查看镜像详细信息
[root@server1 ~]# docker inspect centos:1
[
{
"Id": "sha256:eeb6ee3f44bd0b5103bb561b4c16bcb82328cfe5809ab675bb17ab3a16c517c9",
"RepoTags": [
"centos:1",
"centos:7"
],
"RepoDigests": [
"centos@sha256:9d4bcbbb213dfd745b58be38b13b996ebb5ac315fe75711bd618426a630e0987"
],
"Parent": "",
"Comment": "",
"Created": "2021-09-15T18:20:23.99863383Z",
"Container": "5e4c7bfd35862166e9efd7532208300600114f0acff8f82fd537a57bdd523fe2",
"ContainerConfig": {
"Hostname": "5e4c7bfd3586",
"Domainname": "",
"User": "",
"AttachStdin": false,
"AttachStdout": false,
"AttachStderr": false,
"Tty": false,
"OpenStdin": false,
"StdinOnce": false,
"Env": [
"PATH=/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin"
],
"Cmd": [
"/bin/sh",
"-c",
"#(nop) ",
"CMD [\"/bin/bash\"]"
],
"Image": "sha256:ba35a4b787c8f11e3b6ed9248c7663b4f27459e9715a1ace09f966259d5ebc3a",
"Volumes": null,
"WorkingDir": "",
"Entrypoint": null,
"OnBuild": null,
"Labels": {
"org.label-schema.build-date": "20201113",
"org.label-schema.license": "GPLv2",
"org.label-schema.name": "CentOS Base Image",
"org.label-schema.schema-version": "1.0",
"org.label-schema.vendor": "CentOS",
"org.opencontainers.image.created": "2020-11-13 00:00:00+00:00",
"org.opencontainers.image.licenses": "GPL-2.0-only",
"org.opencontainers.image.title": "CentOS Base Image",
"org.opencontainers.image.vendor": "CentOS"
}
},
"DockerVersion": "20.10.7",
"Author": "",
"Config": {
"Hostname": "",
"Domainname": "",
"User": "",
"AttachStdin": false,
"AttachStdout": false,
"AttachStderr": false,
"Tty": false,
"OpenStdin": false,
"StdinOnce": false,
"Env": [
"PATH=/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin"
],
"Cmd": [
"/bin/bash"
],
"Image": "sha256:ba35a4b787c8f11e3b6ed9248c7663b4f27459e9715a1ace09f966259d5ebc3a",
"Volumes": null,
"WorkingDir": "",
"Entrypoint": null,
"OnBuild": null,
"Labels": {
"org.label-schema.build-date": "20201113",
"org.label-schema.license": "GPLv2",
"org.label-schema.name": "CentOS Base Image",
"org.label-schema.schema-version": "1.0",
"org.label-schema.vendor": "CentOS",
"org.opencontainers.image.created": "2020-11-13 00:00:00+00:00",
"org.opencontainers.image.licenses": "GPL-2.0-only",
"org.opencontainers.image.title": "CentOS Base Image",
"org.opencontainers.image.vendor": "CentOS"
}
},
"Architecture": "amd64",
"Os": "linux",
"Size": 203936249,
"VirtualSize": 203936249,
"GraphDriver": {
"Data": {
"MergedDir": "/var/lib/docker/overlay2/97a00fcfa569398caaea92950c9c34355e757312c712ea042258ecb394873135/merged",
"UpperDir": "/var/lib/docker/overlay2/97a00fcfa569398caaea92950c9c34355e757312c712ea042258ecb394873135/diff",
"WorkDir": "/var/lib/docker/overlay2/97a00fcfa569398caaea92950c9c34355e757312c712ea042258ecb394873135/work"
},
"Name": "overlay2"
},
"RootFS": {
"Type": "layers",
"Layers": [
"sha256:174f5685490326fc0a1c0f5570b8663732189b327007e47ff13d2ca59673db02"
]
},
"Metadata": {
"LastTagTime": "2022-03-18T20:43:29.8170514+08:00"
}
}
]
docker history:查看各层的创建信息
[root@server1 ~]# docker history centos:1
IMAGE CREATED CREATED BY SIZE COMMENT
eeb6ee3f44bd 6 months ago /bin/sh -c #(nop) CMD ["/bin/bash"] 0B
<missing> 6 months ago /bin/sh -c #(nop) LABEL org.label-schema.sc… 0B
<missing> 6 months ago /bin/sh -c #(nop) ADD file:b3ebbe8bd304723d4… 204MB
[root@server1 ~]# docker images
REPOSITORY TAG IMAGE ID CREATED SIZE
nginx latest c919045c4c2b 2 weeks ago 142MB
hello-world latest feb5d9fea6a5 5 months ago 13.3kB
centos 7 eeb6ee3f44bd 6 months ago 204MB
[root@server1 ~]# docker rmi feb5d9fea6a5
Untagged: hello-world:latest
Untagged: hello-world@sha256:2498fce14358aa50ead0cc6c19990fc6ff866ce72aeb5546e1d59caac3d0d60f
Deleted: sha256:feb5d9fea6a5e9606aa995e879d862b825965ba48de054caab5ef356dc6b3412
Deleted: sha256:e07ee1baac5fae6a26f30cabfe54a36d3402f96afda318fe0a96cec4ca393359
[root@server1 ~]# docker images
REPOSITORY TAG IMAGE ID CREATED SIZE
nginx latest c919045c4c2b 2 weeks ago 142MB
centos 7 eeb6ee3f44bd 6 months ago 204MB
修改镜像标签
[root@server1 ~]# docker images
REPOSITORY TAG IMAGE ID CREATED SIZE
nginx latest c919045c4c2b 2 weeks ago 142MB
centos 7 eeb6ee3f44bd 6 months ago 204MB
[root@server1 ~]# docker tag centos:7 centos:1
[root@server1 ~]# docker images
REPOSITORY TAG IMAGE ID CREATED SIZE
nginx latest c919045c4c2b 2 weeks ago 142MB
centos 1 eeb6ee3f44bd 6 months ago 204MB
centos 7 eeb6ee3f44bd 6 months ago 204MB
可以把本地的镜像导出为一个压缩文件,复制到其他服务器导入使用
导出
docker save 镜像:标签 > /path/name.tar.gz
导入
docker load < /path/name.tar.gz
create创建了一个容器但是不启动他,如果想要启动还需要docker start,语法同run
选项 | 说明 |
---|---|
-d | 后台运行容器 |
-i | 保持标准输入打开 |
-t | 分配一个终端,常和i一起用 |
-p | 指定端口映射 |
-P | 通过NAT随机端口映射 |
-rm | 容器退出后就自动删除,不能和-d同时使用 |
-name | 别名 |
-h | 指定容器内的主机名 |
-e | 指定容器内的环境变量 |
-cpu-shares | 允许使用cpu的相对权重,默认一个容器能用满一个核 |
-cpuset-cpus | 限制容器能使用哪些cpu核心 |
-m | 限制容器使用的内存 |
启动一个容器
[root@server1 ~]# docker run -it centos:1 #创建个终端并使用
[root@2bf2fab97e80 /]# exit
exit
[root@server1 ~]# docker ps -a
CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES
2bf2fab97e80 centos:1 "/bin/bash" 31 seconds ago Exited (0) 5 seconds ago nice_ellis
[root@server1 ~]# docker run -it -d centos:1#创建个终端并放在后台运行(不进入)
90f1f6e5df2ee13cfc76553f5d4aef6ff8afe240dfc54dea2f4b3d827033440a
[root@server1 ~]# docker ps -a
CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES
90f1f6e5df2e centos:1 "/bin/bash" 15 seconds ago Up 13 seconds wizardly_chatelet
2bf2fab97e80 centos:1 "/bin/bash" About a minute ago Exited (0) 36 seconds ago nice_ellis
-a :显示所有
-q:只显示容器编号
-n:只显示最近创建的n个容器
[root@server1 ~]# docker run -it -d -P nginx #从32768开始随机映射
74880fe87ea549641f40b009a2fa80b989f47492aed4a76b606f52566150608e
[root@server1 ~]# docker run -it -d -p 80:80 nginx #指定映射
b01711c7814987a915b8199de0d77166ac9d2c38643dd23d14a8a1c82440b879
[root@server1 ~]# docker ps -a
CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES
b01711c78149 nginx "/docker-entrypoint.…" 4 seconds ago Up 3 seconds 0.0.0.0:80->80/tcp, :::80->80/tcp hardcore_meitner
74880fe87ea5 nginx "/docker-entrypoint.…" 12 seconds ago Up 10 seconds 0.0.0.0:49153->80/tcp, :::49153->80/tcp nervous_swirles
[root@server1 ~]# docker port b01711c78149
80/tcp -> 0.0.0.0:80
80/tcp -> :::80
容器需要一个前台进程才能保持运行,启动时的指令可以通过在run时后面添加运行指令,也可以在构建镜像的时候指定容器运行时的前台命令
[root@server1 ~]# docker run -it -d centos:1 ping baidu.com
01a5e3f3e8637b9b6b64c6bf014951911cc87d91c871bd41c9c2256236324397
[root@server1 ~]# docker ps -a
CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES
01a5e3f3e863 centos:1 "ping baidu.com" 5 seconds ago Up 4 seconds flamboyant_bohr
单次运行,运行完就退出
[root@server1 ~]# docker run --rm hello-world
Hello from Docker!
This message shows that your installation appears to be working correctly.
To generate this message, Docker took the following steps:
1. The Docker client contacted the Docker daemon.
2. The Docker daemon pulled the "hello-world" image from the Docker Hub.
(amd64)
3. The Docker daemon created a new container from that image which runs the
executable that produces the output you are currently reading.
4. The Docker daemon streamed that output to the Docker client, which sent it
to your terminal.
To try something more ambitious, you can run an Ubuntu container with:
$ docker run -it ubuntu bash
Share images, automate workflows, and more with a free Docker ID:
https://hub.docker.com/
For more examples and ideas, visit:
https://docs.docker.com/get-started/
[root@server1 ~]# docker ps -a
CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES
挂起:docker pause
取消挂起:docker unpause
终止:docker stop
atach:退出后容器关闭
exec:单次进入,退出后容器仍在运行
-d :分离模式: 在后台运行
-i :即使没有附加也保持STDIN 打开
-t :分配一个伪终端
[root@server1 ~]# docker exec -it d599ed1cfe2f bash #进入容器分配终端并执行bash
[root@d599ed1cfe2f /]#
nsenter:通过pid进入容器内部,可以方便写成脚本操作
#!/bin/bash
docker_in()
{
DOCKER_ID=$1
PID=`docker inspect -f "{{.State.Pid}}" ${DOCKER_ID}`
nsenter -t ${PID} -m -u -i -n -p
}
docker_in $1
docker rm ID
如需要删掉正在运行的容器,则需要加-r
全部删除
docker rm -f `docker ps -aq`
默认采用宿主机,也可以用--dns来指定
docker run -it --rm --dns 8.8.8.8 centos bash
可以把正在跑的容器导出,但是导入的时候会变成镜像
导出
docker export -o /path/name.tar 容器
导入
docker import /path/name.tar 镜像:tag
docker commit -a "作者" -m "提交时是说明文字" ID 镜像名:标签
dockerfile可以当成一种被docker程序解释的脚本,dockerfile由一条条命令组成,每条命令对应linux下的一条命令,docker讲这些指令翻译成真正的linux命令,并更具指令生成镜像,当之后某个镜像有额外的需求时,只需要在之前的dockerfile添加或修改相应的操作就可以重新生成新的docker镜像。
dockerfile指令每一次执行都会在docker上新建一层,过多无意义的层会导致镜像膨胀过大
dockerfile制作一个镜像的流程:
配置指令:
ARG 定义创建镜像过程中使用的变量,不区分大小写
FROM 指定所创建镜像的基础镜像
LABEL 为生成的镜像添加元数据标签信息
EXPOSE 声明镜像内服务监听的端口,只做声明,没有实际映射功能
ENV 指定环境变量
ENTRYPOINT 指定镜像的默认入口命令,每个file只有一个entrypoint能起效,写多个时最后一个起效,ENTRYPOINT command param1 param2
VOLUME 创建一个数据卷挂载点
USER 指定运行容器时的用户名或UID
WORKDIR 配置工作目录
ONBUILD 创建子镜像时指定自动执行的操作指令
STOPSIGNAL 指定退出的信号值
HEALTHCHECK 配置所启动容器如何进行健康检查
SHELL 指定默认shell类型
操作指令:
RUN 运行指定命令
CMD
CMD ["executable","param1","param2"] 相当于执行 executable param1 param2
CMD command param1 param2 在默认的shell中执行,提供给需要交互的应用
CMD ["param1","param2"] 提供给 ENTRYPOINT 的默认参数
启动容器时指定默认执行的命令,cmd跟entrypoint在跟完整命令时功能相似,但是他们并不互斥,可以采用两者相结合的方式来写file,如ent指定默认的运行命令,cmd指定运行参数。如下
ENTRYPOINT ["/bin/ping","-c","3"]
CMD ["localhost"]
ADD <src> <dest>添加内容到镜像
COPY <src> <dest>复制内容到镜像
https://cr.console.aliyun.com/
个人实例--设置密码--命名空间--创建仓库--修改镜像tag--上传镜像
一下命令可以在对应仓库--基本信息里面看到
登录:docker login --username=阿里云账号全名 registry.cn-hangzhou.aliyuncs.com
从仓库中拉取镜像docker pull registry.cn-hangzhou.aliyuncs.com/tokugawa/test1:[镜像版本号]
将镜像推送到仓库
$ docker login --username= registry.cn-hangzhou.aliyuncs.com
$ docker tag [ImageId] registry.cn-hangzhou.aliyuncs.com/tokugawa/test1:[镜像版本号]
$ docker push registry.cn-hangzhou.aliyuncs.com/tokugawa/test1:[镜像版本号]
请根据实际镜像信息替换示例中的[ImageId]和[镜像版本号]参数
[root@server1 tmp]# mkdir nginx
[root@server1 tmp]# cd nginx/
[root@server1 nginx]# wget http://nginx.org/download/nginx-1.2.1.tar.gz
[root@server1 nginx]# ls
nginx-1.2.1.tar.gz
[root@server1 nginx]# vim Dockerfile
#定义基础镜像
FROM centos:7
#维护者信息
MAINTAINER tokugawa 123.qq.com
#编译安装组件
RUN yum install -y vim wget tree lrzsz gcc gcc-c++ automake pcre pcre-devel zlib zlib-devel openssl openssl-devel iproute net-tools iotop
#添加压缩包,一定要处于当前目录下
ADD nginx-1.2.1.tar.gz /usr/local
#配置nginx
RUN cd /usr/local/nginx-1.2.1/ \
&& ./configure --prefix=/usr/local/nginx --with-http_sub_module \
&& make \
&& make install \
&& cd /usr/local/nginx \
&& useradd -s /sbin/nologin nginx \
&& ln -sv /usr/local/nginx/sbin/nginx /usr/sbin/nginx \
&& echo 'test index' > /usr/local/nginx/html/index.html
EXPOSE 80 443
#指定镜像启动进程,让nginx以前台的方式运行
CMD ["nginx", "-g", "daemon off;"]
# 构建镜像,后面有个点不要漏掉!!!!!!!
[root@server1 nginx]# docker build -t nginx:v1 .
如果在构建过程中看docker,会发现有个进程在跑,那个就是新镜像的基地镜像在根据你的设置进行修改
[root@server1 nginx-1.2.1]# docker ps
CONTAINER ID IMAGE COMMAND CREATED STATUS PORTS NAMES
101702c41092 b845f75491a3 "/bin/sh -c 'yum ins…" 32 seconds ago Up 30 seconds gracious_feynman
#弄完看见多了一个镜像
[root@server1 nginx]# docker images
REPOSITORY TAG IMAGE ID CREATED SIZE
centos-nginx v1 0b4c25729f54 43 seconds ago 553MB
nginx latest c919045c4c2b 2 weeks ago 142MB
hello-world latest feb5d9fea6a5 5 months ago 13.3kB
centos 1 eeb6ee3f44bd 6 months ago 204MB
centos 7 eeb6ee3f44bd 6 months ago 204MB
#测试
[root@server1 nginx]# docker run -it -d -p 80:80 centos-nginx:v1
30ccc68e51ca1620b972ab44f0fe79cf9de164d0ea5c04289f70bd19133b30f2
[root@server1 nginx]# curl 192.168.226.148
test index
#传上阿里云
[root@server1 nginx]# docker login --username= registry.cn-hangzhou.aliyuncs.com
Password:
WARNING! Your password will be stored unencrypted in /root/.docker/config.json.
Configure a credential helper to remove this warning. See
https://docs.docker.com/engine/reference/commandline/login/#credentials-store
Login Succeeded
[root@server1 nginx]# docker tag 0b4c25729f54 registry.cn-hangzhou.aliyuncs.com/tokugawa/test1:centos-nginx:v1
Error parsing reference: "registry.cn-hangzhou.aliyuncs.com/tokugawa/test1:centos-nginx:v1" is not a valid repository/tag: invalid reference format
[root@server1 nginx]# docker tag 0b4c25729f54 registry.cn-hangzhou.aliyuncs.com/tokugawa/test1:v1
[root@server1 nginx]# docker push registry.cn-hangzhou.aliyuncs.com/tokugawa/test1:v1
联合挂载是一种文件系统,他可以在不修改原始源的情况下创建多个目录,并把内容合并为一个文件的错觉,docker就采用了这种技术。docker的镜像是分层涉及的,且镜像层是只读的,通过镜像启动的容器添加了一层可读写的文件系统,用户写入的数据就保存在这一层中。每个容器会分配读写层,不同容器会共享同个镜像的制度曾,我们保存在读写层中的数据会在容器被销毁后丢失,为了防止这种情况,我们可以通过数据卷或者数据卷容器的方式将容器内部的数据挂载都本地宿主机的目录,这样在容器被销毁后数据依然存在。
"Data": {
"LowerDir": "/var/lib/docker/overlay2/8ceac458023aa93ad2e2fefb6854fed17fa2899710a3593148194286cca6f52c/diff:/var/lib/docker/overlay2/010397015f4f99b4862a0af74065ac93755bff65ccfd7987991e5c544e8255d4/diff:/var/lib/docker/overlay2/01151daf0f2b878a038de5331732e86c0f90da0094197b1fcfd87ae6fc1116c0/diff:/var/lib/docker/overlay2/ee5b6a585a634ebc9f5e18de5d6ee65c2bd370039a766921de149759ed3e0b80/diff:/var/lib/docker/overlay2/1b95802314d82d8b3f9633013e1ef984b28fdbac717c2dc27be59842db4dc06f/diff",
"MergedDir": "/var/lib/docker/overlay2/0b63610489abe1a4135a80c5f01505a56c3fedd43d37ca2575531c8aa71c1323/merged",
"UpperDir": "/var/lib/docker/overlay2/0b63610489abe1a4135a80c5f01505a56c3fedd43d37ca2575531c8aa71c1323/diff",
"WorkDir": "/var/lib/docker/overlay2/0b63610489abe1a4135a80c5f01505a56c3fedd43d37ca2575531c8aa71c1323/work"
},
LoweDir:image镜像层(只读)
UpperDir:容器上层读写曾
MergeDir:容器文件系统,使用联合文件系统将镜像层和容器曾合并给容器使用
WorkDir:容器在宿主机的工作目录
数据卷实际就是宿主机上的目录或者文件,可以直接挂载到容器当中使用
创建目录,创建容器并挂载,验证
[root@server1 ~]# docker run -d -it --name ser1 -v /tmp/web/:/usr/share/nginx/html -p 80:80 nginx
afe02569c5ff5c640004b31ea903b150864492e6acb8a4fc9280b5d7964e8f0a
[root@server1 ~]# docker run -d -it --name ser2 -v /tmp/web/:/usr/share/nginx/html -p 81:80 nginx
eddc33c5b2c76267b50da429b988aec49467d9109dee9f8f9148004b7e6af705
[root@server1 ~]# curl 192.168.226.148
hello nginx!
[root@server1 ~]# curl 192.168.226.148:81
hello nginx!
修改后同步
[root@server1 ~]# docker exec -it ser1 bash
root@afe02569c5ff:/# echo 'hello ser!' > /usr/share/nginx/html/index.html
root@afe02569c5ff:/# exit
exit
[root@server1 ~]# curl 192.168.226.148:81
hello ser!
[root@server1 ~]# curl 192.168.226.148
hello ser!
只读挂载
[root@server1 ~]# docker run -it -d -p 82:80 -v /tmp/web/:/usr/share/nginx/html:ro nginx
[root@server1 ~]# docker exec -it 195364402ff7 bash
root@195364402ff7:/# echo 'hello!' >/usr/share/nginx/html/index.html
bash: /usr/share/nginx/html/index.html: Read-only file system
文件挂载
docker run -d -it --name web2 -v /data/web/index.html:/usr/share/nginx/html/index.html:ro -p 8081:80 nginx
数据卷容器可以让数据在docker容器之间共享,首先创建一个容器作为server用于卷提供,其他使用这个卷的容器作为客户端
创建卷容器
[root@server1 ~]# docker run -d -it --name web1 -p 8082:80 -v /tmp/web/:/usr/share/nginx/html:ro nginx
启动两个客户端容器
[root@server1 ~]# docker run -d -it --name cli1 -p 8083:80 --volumes-from web1 nginx
78942255bbec92f8fa9473d2b3a56d49a434e534ec152ccb0a5689e595ca6024
[root@server1 ~]# docker run -d -it --name cli2 -p 8084:80 --volumes-from web1 nginx
ddeaff99b9303739d7426ccd3118f3e6cf00acfc5b5a59a26125dac0aef63ffe
[root@server1 ~]# curl 192.168.226.148:8083
hello ser!
[root@server1 ~]# curl 192.168.226.148:8084
hello ser!
卷容器stop后也可以创建新容器,但是卷容器被删除后不可以再创建新容器
用ip进行通信
[root@docker-server1 ~]# docker run -d -it --name web1 nginx [root@docker-server1 ~]# docker run -d -it --name web2 --link web1 nginx
web2的hosts文件会对web1进行解析
[root@docker-server1 ~]# docker exec -it web2 bash
root@8a3e9cee9e37:/# cat /etc/hosts
127.0.0.1 localhost
::1 localhost ip6-localhost ip6-loopback
fe00::0 ip6-localnet
ff00::0 ip6-mcastprefix
ff02::1 ip6-allnodes
ff02::2 ip6-allrouters
172.17.0.2 web1 622eff54876f
172.17.0.3 8a3e9cee9e37
使用别名互联后可以防止出现因为容器改名而无法联通
docker run -d -it --name web3 --link web1:nginx-web1 nginx
[root@docker-server1 ~]# docker exec -it web3 bash
root@c85c73ebf00b:/# cat /etc/hosts
127.0.0.1 localhost
::1 localhost ip6-localhost ip6-loopback
fe00::0 ip6-localnet
ff00::0 ip6-mcastprefix
ff02::1 ip6-allnodes
ff02::2 ip6-allrouters
172.17.0.2 nginx-web1 622eff54876f web1
172.17.0.4 c85c73ebf00b
|网络模式|配置|说明|
|host|–net=host|容器和宿主机共享Network namespace|
|container|–net=container:NAME_or_ID|容器和另外一个容器共享Network namespace。|
|none|–net=none|容器有独立的Network namespace,但并没有对其进行任何网络设置,如分配veth pair 和网桥连接,配置IP等。|
|bridge|–net=bridge|默认|
dockers的默认网络类型。当dockers进程启动时,会再主机上创建一个docker0的虚拟网桥,此时再启动容器就会链接到这个虚拟网桥上,类似于交换机,这个主机上的所有容器就能通过网桥链接再一个二层网络中
dockers0从子网中分配一个ip给容器使用,并把docker0的ip地址作为容器的默认网关,再主机上创建一对veth pair设备,一段放在新创建的容器的,并命名为eth0作为容器的网卡,另一端放在主机中,以vethxx命名,当这个网络设备加入到docker0中,可以通过brctl show查看
容器将跟宿主机共用一个network namespace,容器将不会虚拟出自己的网卡、IP等,而是使用宿主机的IP和端口。host的优点是网络性能好,但是宿主机上已经使用的端口就不能再用了,另外网络的隔离性也不好
[root@docker-server1 ~]# docker run -d -it --name web7 --network host nginx
container的容器和已存在的一个容器共享一个network namespace,除此以外其他的文件系统、进程等还是隔离的,两个容器的进程可以通过lo网卡设备进行通信.注意,当新容器需要的端口已经被老容器占用的时候,可能会导致错误
[root@docker-server1 ~]# docker run -d -it --name web5 --network container:web1 nginx
在使用none后,docker容器不会进行仍和网络配置
`[root@docker-server1 ~]# docker run -d -it --name web4 --network none nginx
1`
创建一个网络
[root@docker-server1 ~]# docker network create -d bridge --subnet 10.10.0.0/16 --gateway 10.10.0.1 testnet
74ee6ecdfc0382ac0abb1b46a3c90e3c6a39f0b7388aa9ba99fddc6bac72e8ce
[root@docker-server1 ~]# docker network list
NETWORK ID NAME DRIVER SCOPE
787342a0d883 bridge bridge local
74ee6ecdfc03 testnet bridge local
9a6d7244e807 host host local
beace8354cca none null local
使用自定义网络[root@docker-server1 ~]# docker run -d -it --name web8 --network testnet nginx
容器在默认情况下没有资源限制但对于linux主机来说,如果没有足够的内存来执行重要的系统任务,那就会抛出OOM异常(内存溢出、内存泄漏、内存异常),之后系统会杀进程来释放内存,为了防止这种情况出现,可以对容器的内存使用范围进行限制
https://blog.csdn.net/shenzhen_zsw/article/details/90722333
-m,–memory 内存限制,格式是数字加单位,单位可以为 b,k,m,g。最小为 4M
–memory-swap 内存+交换分区大小总限制。格式同上。必须必-m设置的大
–memory-reservation 内存的软性限制。格式同上
–oom-kill-disable 是否阻止 OOM killer 杀死容器,默认没设置
–oom-score-adj 容器被 OOM killer 杀死的优先级,范围是[-1000, 1000],默认为 0
–memory-swappiness 用于设置容器的虚拟内存控制行为。值为 0~100 之间的整数
–kernel-memory 核心内存限制。格式同上,最小为 4M
容器测压镜像
[root@server1 ~]# docker pull lorel/docker-stress-ng
FTP:文件传输协议,采用两个TCP连接来传输一个文件
当文件开始在客户和服务器之间传输时,创建一个数据连接(20),具体过程如下:
主动模式
但有时FTP服务器处在的环境不允许直接被外部的主机访问,这时需要采用被动模式,让FTP服务端去连接客户端。具体如下
修改配置文件后重启
vi /etc/vsftpd/vsftpd.conf anonymous_enable=YES
anon_umask=022
anon_upload_enable=Yes anon_mkdir_write_enable=Yes
anon_other_write_enable=Yes local_enable=YES
write_enable=YES
local_umask=022
dirmessage_enable=YES xferlog_enable=YES connect_from_port_20=YES xferlog_std_format=YES
listen=NO
listen_ipv6=YES pam_service_name=vsftpd userlist_enable=YES
tcp_wrappers=YES
修改配置文件后重启
vi /etc/vsftpd/vsftpd.conf
anonymous_enable=NO
local_enable=YES
write_enable=YES
local_umask=022
dirmessage_enable=YES xferlog_enable=YES connect_from_port_20=YES xferlog_std_format=YES
listen=NO
listen_ipv6=YES pam_service_name=vsftpd userlist_enable=YES
tcp_wrappers=YES
在/etc/vsftpd/ftpuser /etc/vsftpd/user_list这两个文件中的用户被视为黑名单
创建FTP用户数据库文件,奇数行用户名,偶数行密码,用db_load命令加密转换成数据库文件,删除明文信息文件
[root@server1 ~]# cd /etc/vsftpd/
[root@server1 vsftpd]# vi vuser.list
[root@server1 vsftpd]# db_load -T -t hash -f vuser.list vuser.db
[root@server1 vsftpd]# file vuser.db
vuser.db: Berkeley DB (Hash, version 9, native byte-order)
[root@server1 vsftpd]# chmod 600 vuser.db
rm -rf vuser.list
创建一个用作代理的本地用户
[root@server1 vsftpd]# useradd -d /var/ftproot -s /sbin/nologin virtual
[root@server1 vsftpd]# ls -ld /var/ftproot/
drwx------. 2 virtual virtual 62 1月 17 18:38 /var/ftproot/
chmod -Rf 777 /var/ftproot
建立一个用于虚拟用户认证的PAM文件
[root@server1 vsftpd]# vi /etc/pam.d/vsftpd.vu
auth required pam_userdb.so db=/etc/vsftpd/vuser account required pam_userdb.so db=/etc/vsftpd/vuser
修改配置文件,注意配置文件每行尾都不能有空格,不然会报错
[root@server1 vsftpd]# cp /etc/vsftpd/vsftpd.conf /etc/vsftpd/vsftpd.conf.bak
[root@server1 vsftpd]# vi /etc/vsftpd/vsftpd.conf
anonymous_enable=NO
local_enable=YES
guest_enable=YES
guest_username=virtual
allow_writeable_chroot=YES
write_enable=YES
local_umask=022
dirmessage_enable=YES
xferlog_enable=YES
connect_from_port_20=YES
xferlog_std_format=YES
listen=NO
listen_ipv6=YES
pam_service_name=vsftpd.vu
userlist_enable=YES
tcp_wrappers=YES
[root@server1 vsftpd]# systemctl restart vsftpd
[root@server1 var]# ftp 192.168.226.148
Connected to 192.168.226.148 (192.168.226.148).
220 (vsFTPd 3.0.2)
Name (192.168.226.148:root): user1
331 Please specify the password.
Password:
230 Login successful.
Remote system type is UNIX.
Using binary mode to transfer files.
一个完整的监控应该包括:
通知告警
zabbix是一个基于web界面提供分布式系统监视以及网络监视功能的开源解决方案
优点
缺点
Zabbix server 是整个 Zabbix 软件的核心程序。
Zabbix Server 负责执行数据的主动轮询和被动获取,计算触发器条件,向用户发送通知。它是 Zabbix Agent 和 Proxy 报告系统可用性和完整性数据的核心组件。Server 自身可以通过简单服务远程检查网络服务(如Web服务器和邮件服务器)。
Zabbix Server是所有配置、统计和操作数据的中央存储中心,也是Zabbix监控系统的告警中心。在监控的系统中出现任何异常,将被发出通知给管理员。
基本的 Zabbix Server 的功能分解成为三个不同的组件。他们是:Zabbix server、Web前端和数据库。
Zabbix 的所有配置信息都存储在 Server 和Web前端进行交互的数据库中。例如,当你通过Web前端(或者API)新增一个监控项时,它会被添加到数据库的监控项表里。然后,Zabbix server 以每分钟一次的频率查询监控项表中的有效项,接着将它存储在 Zabbix server 中的缓存里。这就是为什么 Zabbix 前端所做的任何更改需要花费两分钟左右才能显示在最新的数据段的原因。
Zabbix agent 部署在被监控目标上,以主动监控本地资源和应用程序(硬盘、内存、处理器统计信息等)。
Zabbix agent 收集本地的操作信息并将数据报告给 Zabbix server 用于进一步处理。一旦出现异常 (例如硬盘空间已满或者有崩溃的服务进程),Zabbix server 会主动警告管理员指定机器上的异常。
Zabbix agents 的极高效率缘于它可以利用本地系统调用来完成统计数据的采集。
Zabbix proxy 是一个可以从一个或多个受监控设备采集监控数据并将信息发送到 Zabbix server 的进程,主要是代表 Zabbix server 工作。 所有收集的数据都在本地缓存,然后传输到 proxy 所属的 Zabbix server。
部署Zabbix proxy 是可选的,但可能非常有利于分担单个 Zabbix server 的负载。 如果只有代理采集数据,则 Zabbix server 上会减少 CPU 和磁盘 I/O 的开销。
Zabbix proxy 是无需本地管理员即可集中监控远程位置、分支机构和网络的理想解决方案。
Zabbix proxy 需要使用独立的数据库
安装:在官网上选择对应版本https://www.zabbix.com/cn/download?zabbix=5.0&os_distribution=centos&os_version=7&db=mysql&ws=nginx,这里我选择5.0+centos7+mysql+nginx,然后根据他下面给出的提示安装
rpm -Uvh https://repo.zabbix.com/zabbix/5.0/rhel/7/x86_64/zabbix-release-5.0-1.el7.noarch.rpm
yum clean all
yum install zabbix-server-mysql zabbix-agent
yum install centos-release-scl
vim /etc/yum.repos.d/zabbix.repo
[zabbix-frontend]
name=Zabbix Official Repository frontend - $basearch
baseurl=http://repo.zabbix.com/zabbix/5.0/rhel/7/$basearch/frontend
enabled=1
配置数据库
yum install mariadb-server.x86_64 -y
创建用户,完成初始化
MariaDB [(none)]> create database zabbix character set utf8 collate utf8_bin;
Query OK, 1 row affected (0.00 sec)
MariaDB [(none)]> create user zabbix@localhost identified by '123456';
Query OK, 0 rows affected (0.00 sec)
MariaDB [(none)]> grant all privileges on zabbix.* to zabbix@localhost;
Query OK, 0 rows affected (0.00 sec)
MariaDB [(none)]> exit
zcat /usr/share/doc/zabbix-server-mysql*/create.sql.gz | mysql -uzabbix -p123456 zabbix
vim /etc/zabbix/zabbix_server.conf
DBUser=zabbix
### Option: DBPassword
# Database password.
# Comment this line if no password is used.
#
# Mandatory: no
# Default:
DBPassword=123456
vim /etc/opt/rh/rh-php72/php-fpm.d/zabbix.conf
server {
listen 80;
server_name 192.168.226.148;
vim /etc/opt/rh/rh-php72/php-fpm.d/zabbix.conf
listen.acl_users = apache,nginx
php_value[date.timezone] = Asia/Shanghai
# systemctl restart zabbix-server zabbix-agent rh-nginx116-nginx rh-php72-php-fpm
# systemctl enable zabbix-server zabbix-agent rh-nginx116-nginx rh-php72-php-fpm
访问ip,显示安装成功
初始账号Admin zabbix,去用户中心换语种,当然,为了安全考虑,最好把密码也换掉。在管理--用户里面可以新增用户
rpm -Uvh https://repo.zabbix.com/zabbix/5.0/rhel/7/x86_64/zabbix-release-5.0-1.el7.noarch.rpm
yum install zabbix-agent -y
[root@server2 ~]# vim /etc/zabbix/zabbix_agentd.conf
Server=192.168.80.148
ServerActive=192.168.80.148
Hostname=server2
systemctl start zabbix-agent
在server面板上
配置(Configuration) → 主机(Hosts)->点击创建主机(Create host)以添加新的主机
所有必填字段均以红色星标标示。
至少需要填写下列字段:
主机名称(Host name)
输入一个主机名称,可以使用字母数字、空格、点”."、中划线"-"、下划线"_"。
组
从右边的选择框中,选择一个或者多个组,然后点击 << 移动它们到'所在组(In groups)'选择框;或者输入一个不存在的组名,zabbix会创建这个组。
所有访问权限都分配到主机组,而不是单独的主机。这也是主机需要属于至少一个组的原因。
IP地址
输入主机的IP地址。注意如果这是Zabbix server的IP地址,它必须是Zabbix agent配置文件中‘Server’参数的值。
其他选项将会使用默认值。
当完成后,点击添加(Add)。你可以在主机列表中看到你新添加的主机。
随后我们要添加模板--应用集--监控项,相同的监控项可以放进应用集,相同的应用集可以放进模板
主机--应用集--创建应用集--监控项--创建监控项(添加到对应的应用集)--监控--最新数据--点击刚才的主机选择应用--等待一段时间后可以查看可视化图表
把模板链接到主机:准备一个模版后,将它链接到一个主机。前往配置(Configuration) → 主机(Hosts),点击'新主机(New host)'打开表单,前往模版(Templates)标签页。
在链接新模版(Link new templates)输入我们刚刚新创建的模板名字,我们所创建的模板的名称应该显示在下拉列表中,请向下滚动以进行选择。请查看模版是否出现在链接新模版(Link new templates)文本框。
把一个已有的模板添加到主机的方式:
转到配置→主机
单击所需的主机并切换到模板选项卡
点击链接指示器旁边的选择
在弹出窗口中选择一个或多个模板
单击主机属性窗体中的添加/更新
客户端:
[root@server2 ~]# cat /etc/zabbix/zabbix_agentd.d/userparameter_nginx.conf UserParameter=nginx_process_num,ps -ef | grep -c [n]ginx
[root@server2 ~]# systemctl restart zabbix-agent.service
去服务器上验证
[root@server1 ~]# yum install zabbix-get.x86_64 -y
#这个能获取别的服务器上的监控数据
[root@server1 ~]# zabbix_get -s 192.168.226.149 -k nginx_process_num
3
#说明配置成功,可以去面板上写了
vim /etc/nginx/conf.d/default.conf
location /nginx-status
{
stub_status on;
access_log off;
allow 127.0.0.1;
deny all;
}
vim /etc/zabbix/zabbix_agentd.d/nginx.conf
UserParameter=Nginx.active,/usr/bin/curl -s "http://127.0.0.1:80/nginx-status" | awk '/Active/ {print $NF}'
UserParameter=Nginx.read,/usr/bin/curl -s "http://127.0.0.1:80/nginx-status" | grep 'Reading' | cut -d" " -f2
UserParameter=Nginx.wrie,/usr/bin/curl -s "http://127.0.0.1:80/nginx-status" | grep 'Writing' | cut -d" " -f4
UserParameter=Nginx.wait,/usr/bin/curl -s "http://127.0.0.1:80/nginx-status" | grep 'Waiting' | cut -d" " -f6
UserParameter=Nginx.accepted,/usr/bin/curl -s "http://127.0.0.1:80/nginx-status" | awk '/^[ \t]+[0-9]+[ \t]+[0-9]+[ \t]+[0-9]+/ {print $1}'
UserParameter=Nginx.handled,/usr/bin/curl -s "http://127.0.0.1:80/nginx-status" | awk '/^[ \t]+[0-9]+[ \t]+[0-9]+[ \t]+[0-9]+/ {print $2}'
UserParameter=Nginx.requests,/usr/bin/curl -s "http://127.0.0.1:80/nginx-status" | awk '/^[ \t]+[0-9]+[ \t]+[0-9]+[ \t]+[0-9]+/ {print $3}'
如果不行,把这里两个ssl的框勾上
我在自己服务器上安装的时候,我原本就有一个编译安装在别的目录的nginx,zabbix又给我装了一个,但是两个都是默认80端口,导致当一个被拉起来的时候另外一个拉不起来,后来去把属于zabbix的nginx配置文件里面的端口全部改掉restart才ok
相关参数:
upstream:定义后端服务器组,会引入一个新的上下文
server:在upstream上下文中server成员,以及相关的参数
least_conn;:最少连接调度算法,当server拥有不同的权重时其为wlc
ip_hash;:源地址hash调度方法
hash :基于指定的key的hash表来实现对请求的调度,此处的key可以直接文本、变量或二者的组
合
keepalive connections;:为每个worker进程保留的空闲的长连接数量;
weight=number # 权重,默认为1;
max_fails=number # 失败尝试最大次数;超出此处指定的次数时,server将被标记为不可用;
fail_timeout=time # 设置将服务器标记为不可用状态的超时时长;
max_conns # 当前的服务器的最大并发连接数;
backup # 将服务器标记为“备用”,即所有服务器均不可用时此服务器才启用;
down # 标记为“不可用
负载均衡算法
轮询(默认): 每个请求按时间顺序逐一分配到不同的后端服务,如果后端某台服务器死机,自动剔
除故障系统,使 用户访问不受影响。
weight(轮询权值):weight的值越大分配到的访问概率越高,主要用于后端每台服务器性能不均
衡的情况下。或 者仅仅为在主从的情况下设置不同的权值,达到合理有效的地利用主机资源
ip_hash:每个请求按访问IP的哈希结果分配,使来自同一个IP的访客固定访问一台后端服务器,
并且可以有效解决 动态网页存在的session共享问题。
fair:比 weight、ip_hash更加智能的负载均衡算法,fair算法可以根据页面大小和加载时间长短智
能地进行负载均 衡,也就是根据后端服务器的响应时间 来分配请求,响应时间短的优先分配。
Nginx本身不支持fair,如果需要这 种调度算法,则必须安装upstream_fair模块。
url_hash:按访问的URL的哈希结果来分配请求,使每个URL定向到一台后端服务器,可以进一步
提高后端缓存服 务器的效率。Nginx本身不支持url_hash,如果需要这种调度算法,则必须安装
Nginx的hash软件包。
七层负载均衡是基于URL等应用层信息的负载均衡,也被成为“内容交换”,主要是通过报文中真正有意义的应用层内容,再加上负载均衡设备设置的服务器选择方式,决定最终选择的服务器
以TCP为例,负载均衡器需要先跟客户端建立连接,才能接收到客户端应用层内容的报文,然后根据报文中的特定字段,再加上负载均衡设置的服务器选择方式,最终选定内部服务器。负载均衡器和客户端与服务器会分别建立TCP连接,在这种情况下更像一个代理服务器
七层负载对设备的要求更高,但是对内容的处理更为灵活,例如访问一个网站的游客量,可以把图片类的请求转发到特定的图片服务器并使用缓存技术,对文字类的请求可以转发到特定的文字服务器并使用压缩技术,极大提高网络的灵活性。而且七层负载的特性也决定了面对SYN Flood攻击时,会在负载均衡器这一步就被拦下,不会影响到后台服务器的正常运行
server1作为反向代理服务器,server3,4,5作为apache web站点
先在后面三台上面配置完apache,然后再server1进行反向代理服务器配置七层代理
[root@server1 ~]# vim /etc/nginx/conf.d/proxy.conf
upstream webs{
server 192.168.226.149 weight=2; #weight为权重,可加可不加
server 192.168.226.153 weight=2;
server 192.168.226.152 weight=6;
}
server {
listen *:8787;
server_name 192.168.226.148:8787;
location{
proxy_pass http://webs;
}
}
测试访问
[root@server1 ~]# for i in {1..20};do curl 192.168.226.148:8787; done
server3
server2
server3
server2
server3
server3
server4
server3
server3
server2
server3
server4
server4
server3
server3
server2
server3
server3
server3
server4
四层负载均衡基于IP+端口,主要通过报文中的目标地址和端口,再加上负载均衡设备设置的服务器选择方式,最终决定内部的服务器,负载均衡器仅作转发功能。
以TCP为例,当负载均衡设备接收到第一个来自客户端的SYN请求时,会通过上述方式选择一个最佳服务器,然后修改报文中目标IP之后直接转发给改服务器,TCP的连接也是客户端跟服务器直接连接,负载均衡设备只起一个类似路由转发的功能
yum默认没装这个模块,yum install -y nginx-mod-stream
vim /etc/nginx/nginx.conf
events {
worker_connections 1024;
}
stream{
upstream sshers{
server 192.168.226.149:22;
server 192.168.226.152:22;
server 192.168.226.153:22;
least_conn;#请求将被传递给当前拥有最少活跃连接的server,同时考虑权重weight的因素
}
server{
listen *:7878;
proxy_pass sshers;
}
}
这里用ssh 7878端口远程登陆来测试