强曰为道
与天地相似,故不违。知周乎万物,而道济天下,故不过。旁行而不流,乐天知命,故不忧.
文档目录

GoAccess 日志分析完全指南 / 07 - 过滤与排除

07 - 过滤与排除

7.1 概述

在分析 Web 日志时,经常需要聚焦于特定子集——例如只看某个时间段的访问、排除爬虫流量、过滤特定状态码等。GoAccess 提供了丰富的过滤与排除机制,帮助你从海量日志中快速提取有价值的信息。

原始日志 (100,000 条)
    │
    ├── 排除爬虫 UA     → -15%
    ├── 排除静态资源    → -30%
    ├── 排除健康检查    → -5%
    ├── 排除内网 IP     → -3%
    └── 日期范围过滤    → -20%
    │
    ▼
有效日志 (27,000 条)   → 精准分析

7.2 日期范围过滤

7.2.1 指定日期范围

# 只分析 2026 年 5 月的日志
goaccess /var/log/nginx/access.log \
  --log-format=COMBINED \
  --date-range=20260501-20260531

# 只分析某一天
goaccess /var/log/nginx/access.log \
  --log-format=COMBINED \
  --date-range=20260510-20260510

# 分析最近一周(配合 shell)
START=$(date -d "7 days ago" +%Y%m%d)
END=$(date +%Y%m%d)
goaccess /var/log/nginx/access.log \
  --log-format=COMBINED \
  --date-range=${START}-${END}

7.2.2 日期范围格式

日期格式必须与日志中的日期格式一致:

日志日期格式过滤日期格式示例
%d/%b/%Y (10/May/2026)YYYYMMDD--date-range=20260501-20260531
%Y-%m-%d (2026-05-10)YYYYMMDD--date-range=20260501-20260531

注意:无论日志中的日期格式如何,--date-range 参数始终使用 YYYYMMDD 格式。

7.2.3 配合 grep 预过滤

对于更灵活的日期过滤,可以先用 grep 过滤再传给 GoAccess:

# 使用 grep 按日期预过滤
grep "10/May/2026" /var/log/nginx/access.log | \
  goaccess --log-format=COMBINED -

# 使用 awk 精确过滤时间段
awk '/10\/May\/2026:1[4-6]/' /var/log/nginx/access.log | \
  goaccess --log-format=COMBINED -

# 过滤一个时间范围
awk '/10\/May\/2026/ && /:1[4-6]:/' /var/log/nginx/access.log | \
  goaccess --log-format=COMBINED -

7.3 状态码过滤

7.3.1 只分析特定状态码

# 只分析 5xx 错误
goaccess /var/log/nginx/access.log \
  --log-format=COMBINED \
  --status-code=500

# 只分析 404 页面
goaccess /var/log/nginx/access.log \
  --log-format=COMBINED \
  --status-code=404

# 只分析 4xx 客户端错误
goaccess /var/log/nginx/access.log \
  --log-format=COMBINED \
  --status-code=4xx

# 分析所有错误(4xx + 5xx)
goaccess /var/log/nginx/access.log \
  --log-format=COMBINED \
  --status-code=4xx \
  --status-code=5xx

7.3.2 状态码通配符

GoAccess 支持以下状态码通配方式:

模式说明示例
200精确匹配只匹配 200
4xx匹配 400-499所有客户端错误
5xx匹配 500-599所有服务器错误
3xx匹配 300-399所有重定向

7.3.3 排除特定状态码

# 排除 200 请求,只看异常请求
# (使用 grep 预过滤)
grep -v '" 200 ' /var/log/nginx/access.log | \
  goaccess --log-format=COMBINED -

# 排除 304(Not Modified)请求
grep -v '" 304 ' /var/log/nginx/access.log | \
  goaccess --log-format=COMBINED -

7.3.4 状态码分析实战

# 场景:排查服务器 500 错误
# 1. 先看 500 错误的请求文件分布
grep '" 500 ' /var/log/nginx/access.log | \
  goaccess --log-format=COMBINED \
  --ignore-panel=REFERRING_SITES \
  --ignore-panel=GEO_LOCATION \
  --ignore-panel=HOSTS \
  --ignore-panel=OS_TOOLS \
  --ignore-panel=BROWSERS \
  -

# 2. 看 500 错误的 IP 分布
grep '" 500 ' /var/log/nginx/access.log | \
  goaccess --log-format=COMBINED \
  --sort-panel=HOSTS,BY_HITS \
  --ignore-panel=REQUESTED_FILES \
  -

7.4 IP 过滤

7.4.1 排除特定 IP

# 排除单个 IP
goaccess /var/log/nginx/access.log \
  --log-format=COMBINED \
  --exclude-ip=192.168.1.100

# 排除多个 IP
goaccess /var/log/nginx/access.log \
  --log-format=COMBINED \
  --exclude-ip=192.168.1.100 \
  --exclude-ip=10.0.0.1 \
  --exclude-ip=172.16.0.5

# 排除本地回环地址
goaccess /var/log/nginx/access.log \
  --log-format=COMBINED \
  --exclude-ip=127.0.0.1 \
  --exclude-ip=::1

7.4.2 排除 IP 范围(CIDR)

GoAccess 不直接支持 CIDR 排除,但可以通过多种方式实现:

# 方法一:使用 grep 过滤整个网段
grep -v -E '^(192\.168\.|10\.|172\.(1[6-9]|2[0-9]|3[01])\.)' \
  /var/log/nginx/access.log | \
  goaccess --log-format=COMBINED -

# 方法二:使用 iptables/ipset 标记后过滤
# 方法三:使用 AWK 排除多个 IP
awk '
  !($1 ~ /^192\.168\./ || $1 ~ /^10\./ || $1 ~ /^172\.(1[6-9]|2[0-9]|3[01])\./)
' /var/log/nginx/access.log | goaccess --log-format=COMBINED -

7.4.3 只分析特定 IP

# 只分析特定 IP 的访问
grep "^192.168.1.100" /var/log/nginx/access.log | \
  goaccess --log-format=COMBINED -

# 只分析某个网段
grep "^10.0.0\." /var/log/nginx/access.log | \
  goaccess --log-format=COMBINED -

7.4.4 排除自身访问

# 自动获取外部 IP 并排除
MY_IP=$(curl -s ifconfig.me)
goaccess /var/log/nginx/access.log \
  --log-format=COMBINED \
  --exclude-ip="${MY_IP}"

7.5 请求排除(正则匹配)

7.5.1 排除特定 URL 模式

# 排除静态资源请求
goaccess /var/log/nginx/access.log \
  --log-format=COMBINED \
  --exclude='\.(css|js|jpg|jpeg|png|gif|ico|svg|woff2?|ttf|eot)$'

# 排除健康检查端点
goaccess /var/log/nginx/access.log \
  --log-format=COMBINED \
  --exclude='^/(health|status|ping|readyz|livez)'

# 排除 API 请求
goaccess /var/log/nginx/access.log \
  --log-format=COMBINED \
  --exclude='^/api/'

# 排除 robots.txt 和 sitemap.xml
goaccess /var/log/nginx/access.log \
  --log-format=COMBINED \
  --exclude='^/(robots\.txt|sitemap\.xml|favicon\.ico)'

7.5.2 排除 User-Agent

# 排除常见爬虫
goaccess /var/log/nginx/access.log \
  --log-format=COMBINED \
  --exclude='(bot|crawler|spider|slurp|baidu|googlebot|bingbot|yandex)'

# 排除监控工具
goaccess /var/log/nginx/access.log \
  --log-format=COMBINED \
  --exclude='(curl|wget|Uptime|Pingdom|NewRelic|Datadog)'

# 排除空 User-Agent
goaccess /var/log/nginx/access.log \
  --log-format=COMBINED \
  --exclude='^-$'

7.5.3 多条件排除组合

# 综合排除:静态资源 + 爬虫 + 健康检查 + 自身IP
MY_IP=$(curl -s ifconfig.me)

goaccess /var/log/nginx/access.log \
  --log-format=COMBINED \
  --exclude-ip="${MY_IP}" \
  --exclude='\.(css|js|jpg|jpeg|png|gif|ico|svg|woff2?|ttf|eot)$' \
  --exclude='/(health|status|ping|readyz|livez)' \
  --exclude='(bot|crawler|spider|slurp)' \
  --exclude='^/(robots\.txt|sitemap\.xml|favicon\.ico)'

7.5.4 正则表达式语法

GoAccess 使用 POSIX 扩展正则表达式(ERE):

模式说明示例
.任意字符a.c 匹配 abc, a1c
*前一个字符重复 0 次或多次ab*c 匹配 ac, abc, abbc
+前一个字符重复 1 次或多次ab+c 匹配 abc, abbc
?前一个字符出现 0 或 1 次ab?c 匹配 ac, abc
^行首^/api 匹配以 /api 开头的行
$行尾.css$ 匹配以 .css 结尾的行
[]字符类[0-9] 匹配数字
|a|b 匹配 ab
()分组(css|js) 匹配 cssjs

7.6 面板忽略

7.6.1 忽略不需要的面板

# 只关注核心指标,忽略不常用的面板
goaccess /var/log/nginx/access.log \
  --log-format=COMBINED \
  --ignore-panel=REFERRING_SITES \
  --ignore-panel=REFERRING_URLS \
  --ignore-panel=GEO_LOCATION \
  --ignore-panel=ASN \
  --ignore-panel=KEYPHRASES \
  --ignore-panel=TLS_VERSIONS

7.6.2 面板名称参考

面板名称说明建议
VISITORS独立访客保留
REQUESTS请求文件保留
REQUESTS_STATIC静态资源可选
NOT_FOUND404 页面保留
HOSTSIP 主机保留
OS操作系统保留
BROWSERS浏览器保留
REFERRING_SITES来源站点可忽略
REFERRING_URLS来源 URL可忽略
STATUS_CODES状态码保留
KEYPHRASES关键词已废弃,建议忽略
GEO_LOCATION地理位置可选
ASNASN可忽略
TLS_VERSIONSTLS 版本可忽略

7.7 面板排序

7.7.1 指定面板排序方式

# 按访客数排序(默认按请求数)
goaccess access.log --log-format=COMBINED \
  --sort-panel=VISITORS,BY_VISITORS

# 按带宽排序
goaccess access.log --log-format=COMBINED \
  --sort-panel=REQUESTS,BY_BANDWIDTH

# 多面板排序
goaccess access.log --log-format=COMBINED \
  --sort-panel=VISITORS,BY_VISITORS \
  --sort-panel=REQUESTS,BY_BANDWIDTH \
  --sort-panel=HOSTS,BY_HITS

7.7.2 排序字段

排序字段说明
BY_HITS按请求数排序
BY_VISITORS按访客数排序
BY_DATA按数据字段排序(字母/数字顺序)
BY_BANDWIDTH按带宽排序
BY_CUMULATIVE_BANDWIDTH按累计带宽排序
BY_AVGTS按平均请求时间排序
BY_CUMTS按累计请求时间排序
BY_MAXTS按最大请求时间排序

7.8 面板启用与禁用

7.8.1 仅启用特定面板

# 只看访客和状态码
goaccess access.log --log-format=COMBINED \
  --enable-panel=VISITORS \
  --enable-panel=STATUS_CODES \
  --enable-panel=REQUESTS

注意:使用 --enable-panel 后,未被明确启用的面板将被隐藏。


7.9 过滤实战场景

场景一:分析真实用户访问(排除爬虫和静态资源)

goaccess /var/log/nginx/access.log \
  --log-format=COMBINED \
  --exclude='\.(css|js|jpg|jpeg|png|gif|ico|svg|woff2?|ttf|eot)(\?|$)' \
  --exclude='(bot|crawler|spider|slurp|baidu|googlebot|bingbot|yandex|Bytespider|GPTBot)' \
  --exclude='/(health|status|ping|readyz|livez)' \
  --exclude-ip=127.0.0.1 \
  -o real_users.html

场景二:排查 500 错误

# 只分析 500 错误
grep '" 500 ' /var/log/nginx/access.log | \
  goaccess --log-format=COMBINED \
  --sort-panel=REQUESTS,BY_HITS \
  --ignore-panel=GEO_LOCATION \
  --ignore-panel=REFERRING_SITES \
  --ignore-panel=REFERRING_URLS \
  -o 500_errors.html

场景三:分析移动端流量

# 只分析移动设备
grep -iE '(mobile|android|iphone|ipad|windows phone)' \
  /var/log/nginx/access.log | \
  goaccess --log-format=COMBINED \
  --sort-panel=REQUESTS,BY_HITS \
  -o mobile_traffic.html

场景四:分析 API 请求

# 只分析 /api/ 开头的请求
grep '"GET /api/\|"POST /api/\|"PUT /api/\|"DELETE /api/' \
  /var/log/nginx/access.log | \
  goaccess --log-format=COMBINED \
  --sort-panel=REQUESTS,BY_HITS \
  --ignore-panel=REFERRING_SITES \
  -o api_analysis.html

场景五:分析搜索引擎流量

# 只分析来自搜索引擎的流量
grep -iE '(google\.com|bing\.com|baidu\.com|sogou\.com|yandex\.)' \
  /var/log/nginx/access.log | \
  goaccess --log-format=COMBINED \
  --sort-panel=REFERRING_SITES,BY_HITS \
  --ignore-panel=HOSTS \
  -o search_traffic.html

场景六:分析高峰时段

# 分析 9:00-18:00 工作时间的访问
awk '
  /:0[9]:/ || /:1[0-7]:/ || /:18:00/
' /var/log/nginx/access.log | \
  goaccess --log-format=COMBINED \
  --sort-panel=REQUESTS,BY_HITS \
  -o work_hours.html

7.10 组合过滤脚本

#!/bin/bash
# filter_analysis.sh — 组合过滤分析脚本

LOG_FILE="/var/log/nginx/access.log"
OUTPUT_DIR="/var/www/html/analysis"
MY_IP=$(curl -s ifconfig.me 2>/dev/null || echo "0.0.0.0")
DATE=$(date +%Y-%m-%d)

mkdir -p "${OUTPUT_DIR}"

# 公共排除参数
EXCLUDES=(
  --exclude-ip="${MY_IP}"
  --exclude='\.(css|js|jpg|jpeg|png|gif|ico|svg|woff2?|ttf|eot)(\?|$)'
  --exclude='(bot|crawler|spider|slurp|Bytespider|GPTBot|ClaudeBot)'
  --exclude='/(health|status|ping|readyz|livez|metrics)'
)

# 1. 全量分析(排除爬虫和静态资源)
echo "生成全量分析报告..."
goaccess "${LOG_FILE}" --log-format=COMBINED \
  "${EXCLUDES[@]}" \
  --html-title="全量分析 - ${DATE}" \
  -o "${OUTPUT_DIR}/full_${DATE}.html" \
  --process-and-exit

# 2. 错误分析
echo "生成错误分析报告..."
grep -E '" (4[0-9]{2}|5[0-9]{2}) ' "${LOG_FILE}" | \
  goaccess --log-format=COMBINED \
  --html-title="错误分析 - ${DATE}" \
  -o "${OUTPUT_DIR}/errors_${DATE}.html" \
  --process-and-exit -

# 3. API 分析
echo "生成 API 分析报告..."
grep '"/api/' "${LOG_FILE}" | \
  goaccess --log-format=COMBINED \
  "${EXCLUDES[@]}" \
  --html-title="API 分析 - ${DATE}" \
  -o "${OUTPUT_DIR}/api_${DATE}.html" \
  --process-and-exit -

# 4. 生成索引页
echo "生成索引页..."
cat > "${OUTPUT_DIR}/index_${DATE}.html" << EOF
<!DOCTYPE html>
<html lang="zh-CN">
<head><meta charset="UTF-8"><title>日志分析 - ${DATE}</title></head>
<body style="font-family:sans-serif;max-width:600px;margin:50px auto;">
  <h1>📊 日志分析报告 - ${DATE}</h1>
  <ul>
    <li><a href="full_${DATE}.html">全量分析</a></li>
    <li><a href="errors_${DATE}.html">错误分析</a></li>
    <li><a href="api_${DATE}.html">API 分析</a></li>
  </ul>
</body>
</html>
EOF

echo "分析完成!报告已生成至 ${OUTPUT_DIR}/"

7.11 小结

过滤类型参数示例
日期范围--date-range--date-range=20260501-20260531
状态码--status-code--status-code=4xx
排除 IP--exclude-ip--exclude-ip=127.0.0.1
排除请求--exclude--exclude='\.(css|js)$'
忽略面板--ignore-panel--ignore-panel=GEO_LOCATION
启用面板--enable-panel--enable-panel=VISITORS
面板排序--sort-panel--sort-panel=VISITORS,BY_VISITORS

下一章

下一章将介绍自定义日志处理,包括多虚拟主机日志分析、日志合并、轮转日志处理和管道输入等高级技巧。

08 - 自定义日志处理


扩展阅读