Apache access_log 集計メモ

このサイトで実践しているApache access_logの整形方法をご紹介。以下の文字列を正規表現一発で解析するのはほぼ不可能に近い。

157.55.39.58 - - 2020/03/08:03:13:09 "GET /wp-content/uploads/2019/06/straightnochaser.mp3 HTTP/1.1" 200 575865 "-" "msnbot/2.0b (+http://search.msn.com/msnbot.htm)"

正規表現パズル好きにはたまらないかもしれない。でも僕には耐えられない。手抜き集計で十分だ。

まずはLogFormat最低限のカスタマイズ。日付を YYYY/MM/DD:hh:mm:ss 形式にしてある。

LogFormat "%h %l %u %{%Y/%m/%d:%H:%M:%S}t \"%r\" %>s %b \"%{Referer}i\" \"%{User-Agent}i\""

元の日付フォーマットでは例えば ”01/Mar/2020″ となってしまいソートができない(Apr → Marとなる)と。他パラメータはデフォルトである。妥当なオプションだと思っている。

これを数えていく。一発では綺麗に整形できないので一時ファイルに出力する。

tmpf="/tmp/date +%Y%m%d%H%M%S.access.sum"

自分のアクセスであろうIPを調べる。 管理画面に入って何かしていて、かつOSやユーザエージェントが自分のアクセスを外すため。

jogai=""

jogai_tmp=grep 管理画面 $logd/access_log* | egrep '(エージェントとか|OSとか)' | awk '{ print $1 }' | awk -F: '{print $NF}' | sort | uniq | tr '\n' ' '

botと画像ファイル、ローカルからのアクセス(Wordpress?)を除外対象とする。力技である。

jogai_tmp="$jogai_tmp bot Bot doing_wp_cron 127.0.0.1 .css .js .png .jpeg .jpg python-request"

今時HTTP/1.0はbotでしょう。POSTは普通のアクセスではない。

jogai_tmp=$jogai_tmp" HTTP/1.0"
jogai_tmp=$jogai_tmp" POST"

egrep用の文字列を作成。(egrepのmanを読むべし)

for t in $jogai_tmp
do
    jogai="$t|$jogai"
done
jogai=echo $jogai | sed 's/|$//'

除外した上で HTTP 200 OKリクエストを抽出する。

cat access_log | egrep -v "$jogai" | grep -w '200' > $tmpf

IPアドレスのユニーク数をカウント。≒ユニークユーザー数である。

printf "IP: "
cat $tmpf | awk '{print $1}' | sort | uniq | wc -l

日付を取り出して sort | uniq -c 。日別アクセス数が分かる。下のロジックは周りくどいかもしれない。要するに YYYY/MM/DD だけ出力して sort | uniq -c やってるだけ。

cat $tmpf | awk '{print $1,$4}' | tr -d '[' | tr -d '-' | awk -F: '{print $1}' | awk '{print $2}' | sort | uniq -c

sedでGET以前の文字列を削除するのがポイント。awk – print $1 すればアクセス先ページを取得できる。

cat $tmpf | sed 's/^.*GET//' | awk '{ print $1 }'  | sort | uniq  -c 

ask -F\” がポイント。$4でリファラー(リンク元ページ)を取得できる。

cat $tmpf | awk -F\" '{print $4}' | sort | uniq -c 

ポイントを繰り返す。sed で GET以前の文字列をバッサリ切る処理と、awk -F\” でダブルクオーテーションを区切り文字としてしまう処理である。これで簡単にGET先とリファラーが取れる。難しく考えない方が上手くいくようだ。

以上。

コメントを残す

メールアドレスが公開されることはありません。 が付いている欄は必須項目です