Loggly나 Splunk 같은 유료 로그 매니지먼트 서비스나 자체 로그 분석 시스템을 만들어서 사용하려면 적지않은 시간과 비용이 들어간다.
ElasticSearch, Redis 등 오픈소스 툴을 사용하여 스케일링이 가능한 로그분석 시스템을 만들어 보자.
시스템의 구성은 다음과 같다:
- Nginx, Apache, Tomcat 등 웹 서버에서 발생하는 로그를 각 서버에 있는Collector Logstash가 수집한다.
- Collector Logstash는 수집한 로그를Redis로 보낸다.
- Indexer Logstash (로그를 database에 적재 하는 Logstash)는 Redis에서 로그를 수집하여 ElasticSearch로 보낸다.
- Kibana는 ElasticSearch에 있는 로그를 분석 + Visualization 한다
1. 웹서버 별 Collector Logstash 설치 및 실행
우선 ElasticSearch가 읽을 수 있는 JSON Format의 로그를 쌓도록 웹서버를 설정한다.(Nginx, Apache, Tomcat 중 해당되는 웹 서버의 절차만 따르면 된다)
다음은 Logstash를 설치하고 쌓인 JSON 로그를 Redis로 보내도록 설정한다.
<Nginx>
ElasticSearch가 읽을 수 있는 JSON format 의 로그를 설정 해보자.
1)우선 로그 파일을 만든다:
~ # touch /var/log/nginx/jsonaccess.log
2)Nginx가 JSON format 의 로그를 저장하도록 nginx.conf 파일에 새로운 log_format와 location을 추가한다.
~ # vim /etc/nginx/nginx.conf
…
http {
log_format main ‘$remote_addr – $remote_user[$time_local] “$request” ‘
‘$status $body_bytes_sent “$http_referer” ‘
‘”$http_user_agent” “$http_x_forwarded_for”‘;
log_format json_format ‘{“@time”: “$time_iso8601”, ‘‘”@fields”: { ‘
‘”host”: “$http_host”, ‘
‘”ip”: “$remote_addr”, ‘
‘”request-time”: “$request_time”, ‘
‘”status”: “$status”, ‘
‘”request”: “$request”, ‘
‘”size”: “$body_bytes_sent”, ‘
‘”user-agent”: “$http_user_agent”, ‘
‘”referrer”: “$http_referer” } }’;…
server {
…
location / {
access_log /var/log/nginx/jsonaccess.log json_format;
}
…
3)Logstash를 설치한다.
*(참고) Logstash를 서비스로 설치하는 방법: https://www.elastic.co/guide/en/logstash/current/package-repositories.html
~ # wget https://download.elastic.co/logstash/logstash/logstash-all-plugins-2.1.0.zip
~ # unzip logstash-all-plugins-2.1.0.zip
4)Logstash가 로그를 수집하고 Redis에 적재 할 수 있도록 설정 파일을 만든다.
~ # cd logstash-2.1.0
logstash-2.1.0 # vim logstash.conf
input {
file {
path => “nginx 로그 파일의 절대경로” (example: “/var/log/nginx/jsonaccess.log”)
type => nginx
codec => json
}}
filter {
geoip {source => “[@fields][ip]}
}
output {
redis {
host => “Redis Host IP” (example: “127.0.0.1”)
port => 6379
data_type => “list”
key => “logstash”
}}
5)Redis에 JSON 포맷의 로그가 적재 됐는지 확인 해본다.
<Apache>
ElasticSearch가 읽을 수 있는 JSON format 의 로그를 만들어 보자.
1)우선 로그 파일을 만든다.
~ # touch /etc/httpd/logs/jsonaccess_log
2)Apache가 JSON format의 로그를 저장하도록 configuration 파일에 새로운LogFormat과 CustomLog를 추가한다.
[root@localhost ~]# vim /etc/httpd/conf/httpd.conf
…
<ifModule log_config_module>
#
# The following directives define some format nicknames for use with
# a CustomLog directive (see below).
#LogFormat “%h %l %u %t “%r” %>s %b “%{Referer}i” “%{User-Agent}i”” combined
LogFormat “%h %l %u %t “%r” %>s %b” common
LogFormat “{ “time”:”%t”, “clientip”:”%a”, “host”:”%V”, “request”:”%U”, “query”:”%q”, “method”:”%m”, “status”:”%>s”, “userAgent”:”%{User-agent}i”, “referer”:”%{Referer}i” }” json_format…
CustomLog “logs/access_log” combined
Customlog “logs/jsonaccess_log” json_format
</IfModule>
…
3)Logstash를 설치 한다.
(참고)Logstash를 서비스로 설치하는 방법:https://www.elastic.co/guide/en/logstash/current/package-repositories.html~ # wget https://download.elastic.co/logstash/logstash/logstash-all-plugins-2.1.0.zip
~ # unzip logstash-all-plugins-2.1.0.zip
4)Logstash가 로그를 수집하고 Redis에 적재 할 수 있도록 설정 파일을 만든다.
~ # cd logstash-2.1.0
logstash-2.1.0 # vim logstash.conf
input {
file {
path => “apache 로그 파일의 절대경로” (example: “/etc/httpd/logs/jsonacces_log”)
type => apache
codec => json
}
}filter {
geoip {source => “clientip”}}
output {
redis {
host => “Redis Host IP” (example: “127.0.0.1”)
port => 6379
data_type => “list”
key => “logstash”}
}
(geoip는 IP를 통해 위치 정보를 추가하는 플러그인이다.)
5)Redis에 JSON 포맷의 로그가 적재 됐는지 확인 해 본다. Apache를 재부팅 하고Logstash를 실행한다:
~ # cd logstash-2.1.0
logstash-2.1.0 # ./bin/logstash -f logstash.conf
<Tomcat>
ElasticSearch가 읽을 수 있는 JSON Format의 로그를 만들기 위해서 Log4j 라는 logging utility를 사용했다.1) Log4j 설치
http://serivires.blogspot.kr/2012/03/tomcat-7x-log4j.html
https://tomcat.apache.org/tomcat-7.0-doc/logging.html#Using_Log4j
2) Log4j 사용
Log4j 설치 후 log4j.properties에 다음을 추가하면 된다.
log4j.rootCategory=WARN, RollingLog
log4j.appender.RollingLog =org.apache.log4j.DailyRollingFileAppender
log4j.appender.RollingLog.File =${catalina.base}/logs/jsonlog
log4j.appender.RollingLog.Append = true
log4j.appender.RollingLog.Encoding =UTF-8
log4j.appender.RollingLog.DatePattern =’.’yyyy-MM-dd’.log’
log4j.appender.RollingLog.layout =net.logstash.log4j.JSONEventLayoutV1
log4j.appender.RollingLog.layout.ConversionPattern = %d [%t] %-5p %c- %m%n
3) JSONEventLayoutV1 설치:
Log4j는 layout에 따라 로그의 포맷이 달라지는데 오픈소스로 제공되는JSONEventLayoutV1을 사용해서 로그를JSON Format으로 설정 해보자.Dependencies: jsonevent-layout.jar, commons-lang-2.4.jar, json-smart-1.1.1.jar
Log4j 의 classpath에 jsonevent-layout-1.7.jar 와 필요한 dependency를 다운받는다.
(여기서는 Log4j 를 tomcat 의 logging utility 로 직접 설치했기 때문에 classpath는 /usr/share/tomcat/lib 이다. Log4j를tomcat 자체가 아닌 특정한 애플리케이션에서 사용한다면 log4j.properties 파일은WEB-INF/classes 에, 필요한 jar 파일은WEB-INF/lib 에 설치하면 된다.)~ # cd /usr/share/tomcat/lib (log4j의 classpath)
lib # wget “http://central.maven.org/maven2/net/logstash/log4j/jsonevent-layout/1.7/jsonevent-layout-1.7.jar”
lib # wget “http://repo1.maven.org/maven2/commons-lang/commons-lang/2.4/commons-lang-2.4.jar”
lib # wget “http://repo1.maven.org/maven2/net/minidev/json-smart/1.1.1/json-smart-1.1.1.jar”
4) Logstash를 설치 한다.
~ # wget https://download.elastic.co/logstash/logstash/logstash-all-plugins-2.1.0.zip
~ # unzip logstash-all-plugins-2.1.0.zip
5) Logstash가 로그를 수집하고 Redis에 적재 할 수 있도록 설정파일을 만든다
~ # cd logstash-2.1.0
logstash-2.1.0 # vim logstash.conf
input {
file {
path => “…/logs/jsonlog” (ex: /usr/share/tomcat/logs/jsonlog)
type => tomcat
codec => json
}}
filter {
geoip {
source => “[@fields][ip]”
}}
output {
redis {
host => “Redis Host IP” (example: “127.0.0.1”)
port => 6379
data_type => “list”
key => “logstash”
}}
2. Redis 설치
~ # wget http://download.redis.io/releases/redis-3.0.7.tar.gz
~ # tar xvfz redis-3.0.7.tar.gz
~ # cd redis-3.0.7/src
src # make
실행 :
src # ./redis-server
src # ./redis-cli
> set foo bar
OK
> get foo
“bar”
3. Logstash, Kibana, ElasticSearch 설치
<(Centos7) Logstash, Kibana, ElasticSearch 설치>
[logstash-2.2] name=Logstash repository for 2.2.x packages
~ # vim /etc/yum.repos.d/logstash.repo
baseurl=http://packages.elastic.co/logstash/2.2/centos
gpgcheck=1
gpgkey=http://packages.elastic.co/GPG-KEY-elasticsearch
enabled=1
~ # yum install logstash
~ # vim /etc/yum.repos.d/elasticsearch.repo[elasticsearch-2.x] name=Elasticsearch repository for 2.x packages
baseurl=http://packages.elastic.co/elasticsearch/2.x/centos
gpgcheck=1
gpgkey=http://packages.elastic.co/GPG-KEY-elasticsearch
Enabled=1
~ # yum install elasticsearch
~ # vim /etc/yum.repos.d/kibana.repo[kibana-4.4] name=Kibana repository for 4.4.x packages
baseurl=http://packages.elastic.co/kibana/4.4/centos
gpgcheck=1
gpgkey=http://packages.elastic.co/GPG-KEY-elasticsearch
enabled=1~ # yum install kibana
<Logstash, ElasticSearch, Kibana 실행/부팅 실행 설정하기>
~ # systemctl enable logstash
~ # systemctl enable kibana
~ # systemctl enable elasticsearch
~ # systemctl start logstash
~ # systemctl start kibana
~ # systemctl start elasticsearch
Centos7 외의 OS에서 Logstash/Kibana/ElasticSearch를 설치하려면 다음 링크를 참고하면 된다.
ElasticSearch: https://www.elastic.co/guide/en/elasticsearch/reference/current/setup-repositories.html
Logstash: https://www.elastic.co/guide/en/logstash/current/package-repositories.html
Kibana: https://www.elastic.co/guide/en/kibana/current/setup.htmltouch
<Indexer Logstash>
Redis에 쌓인 로그들을 ElasticSearch로Indexing하는 Logstash를 설정해보자. Redis 로그를 ElasticSearch에 적재하기 위한 설정 파일을 만든다
~ # cd /etc/logstash/conf.d
conf.d # vim logstash.conf
input {
redis {
host => “Redis host IP”
port => 6379
codec => json
data_type => “list”
key => “logstash”}
}
output {
elasticsearch {}
}
Logstash를 실행해서 Redis에 있던 로그들이 Kibana에 올라왔는지 확인 해본다.
References:
(1) http://brantiffy.axisj.com/archives/418 , “5.Nginx 로그 설정”(2)https://blog.logentries.com/2014/08/json-logging-in-apache-and-nginx-with-logentries/
(3) http://mvnrepository.com/artifact/net.logstash.log4j/jsonevent-layout/1.0
(4) http://redis.io/download