HTTPSでnginx_statusが取れない
MuninでHTTPSのnginx_status取得が失敗して、グラフが描画されない時の対処方法を書く。
Munin version 2.0.25
CentOS 6
事象
nginx.confが80ポートのHTTPの時は問題なくグラグが描画された。
server {
listen 80;
listen localhost:80;
略
location /nginx_status {
stub_status on;
access_log off;
allow 127.0.0.1;
deny all;
}
}
これを443ポートのHTTPSに変更すると、グラフが描画されなくなった。
server {
listen 443;
listen localhost;443;
略
location /nginx_status {
stub_status on;
access_log off;
allow 127.0.0.1;
deny all;
}
}
調査
このサーバでmunin-runを実行してmuninの挙動を確かめてみる。
$ sudo munin-run nginx_status
total.value U
reading.value U
writing.value U
waiting.value U
$ sudo munin-run nginx_request
request.value U
nginx_statusプラグインもnginx_requestプラグインも取得した値が数値ではなくUという文字列になってしまった。これらのプラグインのコードを確認してみると、URLがHTTPを前提として動いているため、HTTPSにアクセスできていないことがわかる。
$ grep URL /usr/share/munin/plugins/nginx_status
my $URL = exists $ENV{'url'} ? $ENV{'url'} : "http://localhost/nginx_status";
my $response = $ua->request(HTTP::Request->new('GET',$URL));
print "no (no nginx status on $URL)\n";
my $response = $ua->request(HTTP::Request->new('GET',$URL));
対処
環境変数urlをhttps://localhost/nginx_status
に変えてみるとうまく動く。
$ url=https://localhost/nginx_status
$ export url
$ sudo munin-run nginx_request
total.value 1
reading.value 0
writing.value 1
waiting.value 0
$ sudo munin-run nginx_request
request.value 10
環境変数urlだけでなく、環境変数 portも変えた方がいい。Nginx requestsグラフの表記がrequests port 80になっているので、443に修正するために環境変数portも指定してあげる。
$ grep port /usr/share/munin/plugins/nginx_request
my $port = exists $ENV{'port'} ? $ENV{'port'} : "80";
print "request.label requests port $port\n";
先ほどはコマンドを打って環境変数を設定したが、環境変数をMunin上で設定するには/etc/munin/plugin-conf.d/munin-node
にenv.変数 値
で記載する。
[nginx*]
env.url https://localhost/nginx_status
env.port 443
記載が終わったらmunin-nodeを再起動する。
$ sudo service munin-node restart
確認
munin-nodeでmunin-runで実行して確認できたら、munin本体からもtelnetやncを使って4949ポートにつなぎ、fetchを発行して確認してみる。
ちなみに、munin-node側ではmunin-node再起動しなくてもmunin-runで環境変数が適用された正しい値が取れることが確認できるが、munin本体から確認するときは、munin-node側でmunin-node再起動していないとfetchで環境変数が適用された正しい値を取れない。もし環境変数も設定ファイルに正しく書いて、munin-runで値が取れることを確認しているのに、グラフ描画が行われない場合は、service munin-node restart
を実行しておらず、munin本体から値が取れていない状況かもしれない。
$ telnet munin-nodeのIP 4949
fetch nginx_status
total.value 1
reading.value 0
writing.value 1
waiting.value 0
.
request.value 26
.
quit
確認しているうちに、munin本体のcronが動き、グラフ描写も始まる。
CentOS 7とMunin 2.0.33で構築したら他にも対処が必要だった
どこが直接の原因かは調べていないが、CentOS 7.5で構築していたところ、上記対策を行ってもMuninの値が取れなかった。
調査
munin-run nginx_request --debug
, munin-run nginx_status --debug
をして確認したところ、環境変数が正しく設定されていることは確認できたが、それ以上の情報は得られなかった。pluginのソースを編集して、Responseの情報を表示できるようにした。
## response取得後に以下を追加
$ sudo vim /usr/share/munin/plugins/nginx_request
print $response->message;
$ sudo munin-run nginx_request
Protocol scheme 'https' is not supported (LWP::Protocol::https not installed)request.value U
HTTPSをサポートしていないといわれてしまった。
http://please-sleep.cou929.nu/lwp-useragent-ssl-warn.htmlによると「LWP::UserAgent は昔は LWP::Protocol::https をバンドルしていたが、次のコミットからは分離するようになった。LWP::UserAgent で SSL 接続する場合は LWP::Protocol::https も別途入れてあげる必要がある」とのこと。
対処
yumでperl-LWP-Protocol-httpsをinstallする。
$ sudo yum install perl-LWP-Protocol-https
調査その2
再度munin-runしたところ、今度は別のエラーがでた。
$ sudo munin-run nginx_request
Can't connect to localhost:443request.value U
自己証明書を入れていたため、証明書の検査を省く必要がありそう。curlでも--insecure
をつけないとつなげない。
$ curl https://localhost:443/nginx_status
curl: (60) Peer's certificate issuer has been marked as not trusted by the user.
More details here: http://curl.haxx.se/docs/sslcerts.html
curl performs SSL certificate verification by default, using a "bundle"
of Certificate Authority (CA) public keys (CA certs). If the default
bundle file isn't adequate, you can specify an alternate file
using the --cacert option.
If this HTTPS server uses a certificate signed by a CA represented in
the bundle, the certificate verification probably failed due to a
problem with the certificate (it might be expired, or the name might
not match the domain name in the URL).
If you'd like to turn off curl's verification of the certificate, use
the -k (or --insecure) option.
$ curl --insecure https://localhost/nginx_status
Active connections: 1
server accepts handled requests
34 34 27
Reading: 0 Writing: 1 Waiting: 0
SSL証明書の対処
Perlでcurlの--insecure
と同じように対応するため、/usr/share/munin/plugins/nginx_requestと/usr/share/munin/plugins/nginx_statusを編集した。以下のコードをLWP::UserAgent->new
の後に入れた。
$ua->ssl_opts( verify_hostname => 0 ,SSL_verify_mode => 0x00);
munin-runで正しく値が取れたため、エラーメッセージを確認するために追加したprint $response->message;
を消したうえでsystemctl restart munin-node
すると、グラフに描画された。