滚动 docker 中的 nginx 日志思路详解

docker使用

  1. docker ps 查看运行中的容器

  2. docker images 查看docker镜像

  3. docker rm id(容器id)  删除容器(容器id可以通过docker ps查看,容器必须停止后才能删除)

    3.1 删除全部的容器 docker rm `docker ps -a -q`

  4. docker stop  id(容器id) 停止容器运行

  5. docker rmi  id(镜像id) 删除镜像

  6. docker pull ubuntu:16.04(镜像名称:版本号) 下载镜像

  7. docker run -it ubuntu:16.04 创建并运行容器容器

    -t 表示在新容器内指定一个伪终端或终端

    -i 表示允许我们对容器内的 (STDIN) 进行交互

    -p 指定映射端口

    -d 在后台运行容器并打印容器ID

    7.1 docker run -dit ubuntu:16.04 创建并后台运行容器

    7.2 docker run -ditp 8080:8080(主机端口:容器端口) ubuntu:16.04 创建并后台运行容器且映射容器的端口

  8. docker attach id(容器id) 进入正在运行中的容器环境

  9. 退出容器

    9.1 exit 直接退出容器并终止容器运行

    9.2 [ctrl+p]+[ctrl+q](快捷键) 退出容器,但是不会终止容器运行

  10. docker commit -m'版本标识' id(容器id) ubuntu:16.04(镜像与版本号)   提交镜像且生成镜像(可以通过该命令把搭建好的容器打包成一个新的镜像或者覆盖原镜像(即是修改原镜像内容,生成的镜像名与版本号相同就可以直接覆盖))

好了,大家了解了docker,下面是本文介绍的重点,一起看看吧。

Nginx 自己没有处理日志的滚动问题,它把这个球踢给了使用者。一般情况下,你可以使用 logrotate 工具来完成这个任务,或者如果你愿意,你可以写各式各样的脚本完成同样的任务。本文笔者介绍如何滚动运行在 docker 中的 nginx 日志文件(下图来自互联网)。

思路

Nginx 官方其实给出了如何滚动日志的说明:

Rotating Log-files
In order to rotate log files, they need to be renamed first. After that USR1 signal should be sent to the master process. The master process will then re-open all currently open log files and assign them an unprivileged user under which the worker processes are running, as an owner. After successful re-opening, the master process closes all open files and sends the message to worker process to ask them to re-open files. Worker processes also open new files and close old files right away. As a result, old files are almost immediately available for post processing, such as compression.

这段说明的大意是:

•先把旧的日志文件重命名
•然后给 nginx master 进程发送 USR1 信号
•nginx master 进程收到信号后会做一些处理,然后要求工作者进程重新打开日志文件
•工作者进程打开新的日志文件并关闭旧的日志文件

其实真正需要我们做的工作只有前面两点!

创建测试环境

假设你的系统中已经安装好了 docker,这里我们直接运行一个 nginx 容器:

$ docker run -d \
 -p 80:80 \
 -v $(pwd)/logs/nginx:/var/log/nginx \
 --restart=always \
 --name=mynginx \
 nginx:1.11.3

注意,我们把 nginx 的日志绑定挂载到了当前目录下的 logs 目录下。

把下面的内容保存到 test.sh 文件中:

#!/bin/bash
for ((i=1;i<=100000;i++))
do
 curl http://localhost > /dev/null
 sleep 1
done

然后运行这个脚本,就可以模拟产生连续的日志记录。

创建滚动日志的脚本

创建 rotatelog.sh 文件,其内容如下:

#!/bin/bash
getdatestring()
{
 TZ='Asia/Chongqing' date "+%Y%m%d%H%M"
}
datestring=$(getdatestring)
mv /var/log/nginx/access.log /var/log/nginx/access.${datestring}.log
mv /var/log/nginx/error.log /var/log/nginx/error.${datestring}.log
kill -USR1 `cat /var/run/nginx.pid`

getdatestring 函数取当前的时间并格式化为字符串,比如 "201807241310",笔者比较喜欢用日期和时间来命名文件。注意这里通过 TZ='Asia/Chongqing' 指定了时区,因为默认情况下格式化的是 UTC 时间,用起来怪怪的(要实时脑补 +8 小时)。下面的两条 mv 命令用来重命名日志文件。最后通过 kill 命令向 nginx master 进程发送 USR1 信号。

通过下面的命令为 rotatelog.sh 文件添加可执行权限并复制到 $(pwd)/logs/nginx 目录下:

$ chmod +x rotatelog.sh
$ sudo cp rotatelog.sh $(pwd)/logs/nginx

定时执行滚动操作

我们的 nginx 运行在容器中,所以需要在容器中给 nginx master 进程发送 USR1 信号。因此我们需要通过 docker exec 命令在 mynginx 容器中执行 rotatelog.sh 脚本:

$ docker exec mynginx bash /var/log/nginx/rotatelog.sh

执行一次上面的命令,会如期产生一批新的日志文件:

下面我们把这个命令配置在定时任务中,让它每天早上 1 点钟执行一次。执行 crontab -e 命令,并在文件的末尾添加下面的行:

* 1 * * * docker exec mynginx bash /var/log/nginx/rotatelog.sh

保存并退出就可以了。下图是笔者测试过程中每 5 分钟滚动一次的效果:

为什么不在宿主机中直接 mv 日志文件?

理论上这么做是可以的,因为通过绑定挂载的数据卷中的内容从宿主机上看和从容器中看都是一样的。但是真正这么做的时候你很可能碰到权限问题。在宿主机中,你一般使用的是普通用户,而在容器中产生的日志文件的所有者是会是特殊的用户,并且一般不会给其它用户写和执行的权限:

当然,如果你在宿主机中使用的是 root 用户就不会有问题。

能从宿主机中发送的信号吗?

其实这个问题的全称应该是:能从宿主机中给 docker 容器中的 nginx master 进程发送信号吗?

答案是,可以的。

笔者这《在 docker 容器中捕获信号》一文中介绍了容器中信号的捕获问题,感兴趣的朋友可以去看看。在那篇文章中我们介绍了 docker 向容器中进程发送信号的 kill 命令。我们可以通过命令:

$ docker container kill mynginx -s USR

向容器中的 1 号进程(nginx master)发送 USR1 信号(这种方式只能向 1 号进程发送信号):

结合上面的两个问题,我们可以写出另外的一种方式来滚动 docker 中的 nginx 日志。这种方式不需要通过 docker exec 命令在容器中执行命令,而完全在宿主机中完成所有的操作:

•先重命名容器数据卷中的日志文件
•给容器中的 1 号进程发送 USR1 信号

参考:

How To Configure Logging and Log Rotation in Nginx on an Ubuntu VPS

How To Manage Logfiles with Logrotate on Ubuntu 16.04

总结

以上所述是小编给大家介绍的滚动 docker 中的 nginx 日志思路详解,希望对大家有所帮助,如果大家有任何疑问请给我留言,小编会及时回复大家的。在此也非常感谢大家对我们网站的支持!

(0)

相关推荐

  • 详解nginx日志定时备份和删除

    一旦开启了nginx日志功能,每天nginx都会生成一定大小的日志文件,如果系统稳定运行,没有任何问题,那么日志基本上不会去查看.但这些日志如不及时清理,日渐积累,对服务器的磁盘空间占用也将是比较恐怖的.为了解决这个问题,利用shell脚本对nginx日志文件定时备份和删除,只保留一段时间. 图1: #!/bin/bash #auth:lzq #desc:把当前日志按日期备份,重新生成第二天的日志文件 #date:2016-09-18 DATE=`date +%Y%m%d` NGINX_PID=

  • 基于nginx access日志格式详解

    nginx的nginx.cnf中,使用log_format字段可以指定日志的格式文件. log.fromat: log_format access ' [$time_local] | $host | $remote_addr | $request | $request_time | $body_bytes_sent | $status |' '| $upstream_addr | $upstream_response_time | $upstream_status |' ' "$http_ref

  • 关于nginx日志增加cookie信息

    一.获取全部cookie信息 这个比较方便,直接在nginx.conf文件中添加$http_cookie log_format main '[$time_local] - $remote_addr:$remote_port - $remote_user - $upstream_addr $upstream_status $upstream_response_time - ' '"$request" $status $bytes_sent $request_time ' '"$

  • nginx日志模块及日志定时切割的方法

    一:作用 Ngx_http_log_module:定义日志格式,并且以指定的格式保存. 二:示例配置 log_format compression '$remote_addr - $remote_user [$time_local] ' '"$request" $status $bytes_sent ' '"$http_referer" "$http_user_agent" "$gzip_ratio"'; access_log

  • CentOS 7.0下nginx实现每天定时分割日志

    环境说明: 操作系统CentOS7.0,默认在线安装nginx. nginx配置文件路径:/etc/nginx/nignx.conf, nginx日志文件路径:/var/log/nginx/access.log nignx.pid路径:/run/nginx.pid 新建的定时脚本位置/shell/nginx/logs.sh 1.新建脚本并执行 #mkdir /shell/nignx #cd /shell/nginx #vim logs.sh #!/bin/bash base_path='/var

  • Nginx自定义访问日志的配置方式

    前言 Nginx日志主要分为两种:访问日志和错误日志.日志开关在Nginx配置文件(/etc/nginx/nginx.conf)中设置,两种日志都可以选择性关闭,默认都是打开的. 访问日志主要记录客户端访问Nginx的每一个请求,格式可以自定义.通过访问日志,你可以得到用户地域来源.跳转来源.使用终端.某个URL访问量等相关信息. 日志的重要性不言而喻,一般来说我们开发过程中会为每个项目定义自己的日志格式以及存储路径. 就我们普通的JAVAWEB项目来说,重要的日志一般输出并存放在Tomcat的

  • Nginx 日志改成 JSON 格式的方法

    Nginx 日志默认为普通文本的格式,例如,下面是 Nginx 的一行访问日志: 10.88.122.105 - - [02/Dec/2017:09:15:04 +0800] "GET /js/pagination.js HTTP/1.1" 304 0 "http://10.88.105.20:8063/stockrecommand.html" "Mozilla/4.0 (compatible; MSIE 7.0; Windows NT 6.1; WOW6

  • nginx日志中添加请求的response日志(推荐)

    由于此功能在nginx内置的功能中没有,需要安装第三方模块ngx_lua,由于此模块需要Lua语言,所以需要安装相应的Lua语言包 1. 下载安装LuaJIT # cd /usr/local/src # wget http://luajit.org/download/LuaJIT-2.0.2.tar.gz # tar -xzvf LuaJIT-2.0.2.tar.gz # cd LuaJIT-2.0.2 # make 出现如下内容表示编译成功 OK Successfully built LuaJ

  • python+pandas分析nginx日志的实例

    需求 通过分析nginx访问日志,获取每个接口响应时间最大值.最小值.平均值及访问量. 实现原理 将nginx日志uriuriupstream_response_time字段存放到pandas的dataframe中,然后通过分组.数据统计功能实现. 实现 1.准备工作 #创建日志目录,用于存放日志 mkdir /home/test/python/log/log #创建文件,用于存放从nginx日志中提取的$uri $upstream_response_time字段 touch /home/tes

  • Nginx日志管理介绍

    Nginx日志描述 通过访问日志,你可以得到用户地域来源.跳转来源.使用终端.某个URL访问量等相关信息:通过错误日志,你可以得到系统某个服务或server的性能瓶颈等.因此,将日志好好利用,你可以得到很多有价值的信息. 参数明细表: $remote_addr 客户端的ip地址(代理服务器,显示代理服务ip) $remote_user 用于记录远程客户端的用户名称(一般为"-") $time_local 用于记录访问时间和时区 $request 用于记录请求的url以及请求方法 $st

  • nginx服务器中access_log日志分析与配置详解

    前言 nginx的log日志分为:access log 和 error log 其中access log 记录了哪些用户,哪些页面以及用户浏览器.ip和其他的访问信息 error log 则是记录服务器错误日志 log_format 日志格式语法: log_format name(格式名字) 格式样式(即想要得到什么样的日志内容) 示例: log_format main '$remote_addr - $remote_user [$time_local] "$request" ' '$

  • Nginx日志统计分析的常用命令总结

    本文主要给大家总结了关于Nginx日志统计分析的一些常用命令,分享出来供大家参考学习,下面来一起看看详细的介绍: 一.IP相关统计 统计IP访问量 awk '{print $1}' access.log | sort -n | uniq | wc -l 查看某一时间段的IP访问量(4-5点) grep "07/Apr/2017:0[4-5]" access.log | awk '{print $1}' | sort | uniq -c| sort -nr | wc -l 查看访问最频繁

随机推荐