구성


이번 편은 지난편에 이어 NodeJS 를 이용하여 customer 메트릭 생성하여 Prometheus에 전달하기 위한 어플리케이션을 만들고, 로컬 docker 환경에서 테스트 하는 방법에 대해 알아 보도록 하겠습니다.

  • Prometheus와 Grafana
  • Prometheus 모니터링 어플리케이션 개발과 로컬 docker를 활용한 테스트





모니터링 어플리케이션


어플리케이션은 prom-client 패키지(https://github.com/siimon/prom-client)를 사용합니다. prom-client는 prometheus의 네가지 주요 메트릭을 모두 지원합니다. 이 외에도 CPU와 메모리등의 기본 시스템 메트릭, 멀티플 레지스트리, 푸쉬 게이트웨이 지원등의 다양한 기능들이 있으니 prom-clinet 패키지 사이트에서 확인해 보시기 바랍니다.

1) 소스 내려 받기

모니터링 어플리케이션 소스는 https://github.com/blbird/PrometheusSampleApp에 있습니다. 해당 소스를 clone 합니다.


git clone https://github.com/blbird/PrometheusSampleApp.git

2) 소스 설명

app.js 파일을 보시면 아래와 같이 5가지 메트릭을 정의하여 사용합니다.


const counter = new promClient.Counter({
  name: 'prom_sample_counter',
  help: 'prom_sample_counter_help',
});

const gauge = new promClient.Gauge({
  name: 'prom_sample_gauge',
  help: 'prom_sample_gauge_help',
});

const labeledGauge = new promClient.Gauge({
  name: 'prom_sample_labeled_gauge',
  help: 'prom_sample_labeled_gauge_help',
  labelNames: ['id'],
}); 

const histogram = new promClient.Histogram({
  name: 'prom_sample_histogram',
  help: 'prom_sample_histogram_help',
  labelNames: ['status_code'],
  buckets: [20, 40, 60, 80, 100],
});

const summary = new promClient.Summary({
  name: 'prom_sample_summary',
  help: 'prom_sample_summary_help',
  labelNames: ['status_code'],
});



각 metric은 아래와 같이 15초 간격으로 값을 변경합니다.

  • prom_sample_counter는 값을 1 증가시키고, prom_sample_gauge는 값이 0부터 10까지 증가했다가 다시 0까지 감소합니다.
  • prom_sample_labeled_gauge는 두개의 “2”와 “3”의 두개의 label을 가지고 있으면 각각 prom_sample_gauge값의 2배, 3배의 값으로 설정이 됩니다.
  • prom_sample_histogram과 prom_sample_summary는 http 리퀘스트의 상태 결과와 걸린 시간을 램덤하게 설정하였습니다.

setInterval(() => {
  // increase counter value
  counter.inc();

  // increase adn decrease gauge value
  if (interval === 1) {
    gauge.inc();
  }
  else {
    gauge.dec();
  }

  cnt += interval;
  if (cnt >= 10) {
    interval = -1;
  }
  else if (cnt <= 0) {
    interval = 1;
  }

  // set labeled gauage value
  labeledGauge.labels('2').set(cnt*2);
  labeledGauge.set({id: '3'}, cnt*3);

  // set histogram value
  const status = Math.floor(Math.random() * statusCodes.length);
  const duration = Math.floor(Math.random() * 100);

  histogram.labels(statusCodes[status]).observe(duration);
  summary.labels(statusCodes[status]).observe(duration);
}, 10000);

3) 어플리케이션 실행


npm install
npm start

4) 어플리케이션 실행 확인

브라우저에서 http://localhost:9100/metrics 를 입력하시면 Prometheus 포맷의 메트릭 값들을 확인하실수 있습니다.




Prometheus 실행

1) Prometheus 설정 파일

받으신 소스에 prometheus.yml 파일이 있습니다. 이 파일은 Prometheus가 실행되기 위한 설정 파일 입니다. 전편에서 말씀드렸듯이 Prometheus는 pull 방식을 사용합니다. 따라서, 메트릭을 읽어올 서버를 지정해 주어야 합니다. 이런 서버를 지정 및 각 종 설정을 위한 파일이 바로 이 prometheus.yml 파일 입니다. global 부분은 전체에 적용되는 부분으로 현재 데이터를 1분마다 가져오는 것으로 설정했습니다. scrape_configs 부분이 있는데, 이 부분이 데이터를 가져오기 위한 서버를 명시하는 부분입니다. 기본적으로 Prometheus 자체의 메트릭을 읽어 오는 설정이 되어 있습니다. 그리고, prom_sample은 위에서 작성한 어플리케이션을 명시하기 위한 부분으로 읽어오기 위한 interval을 15초로 설정하고 있고 해당 어플리케이션의 주소를 입력하는 부분이 있습니다. 따라서 해당 어플리케이션에서 모니터링 데이터를 읽어오기 위해 부분을 어플리케이션이 실행되고 있는 주소로 변경하셔야 합니다.


global:
  scrape_interval: 1m

scrape_configs:
  - job_name: 'prometheus'
    static_configs:
    - targets: ['localhost:9090']
  - job_name: 'prom_sample'
    scrape_interval: 15s
    static_configs:
    - targets: ['target address:9100']

2) Prometheus docker 컨테이너 생성

아래 명령어를 통해 Prometheus용 docker 컨테이너를 생성합니다. -p 옵션을 통해 Prometheus ui를 보여주기 위한 포트를 localhost의 포트로 매핑해 줍니다. -v 옵션은 위의 설정한 파일을 docker의 prometheus 실행파일에서 읽을수 있도록 docker상의 파일 링크로 마운트 하기 위한 것입니다.


docker run -d -p 9090:9090 -v `pwd`/prometheus.yml:/etc/prometheus/prometheus.yml prom/prometheus

3) Prometheus UI

실행이 완료되면 http://localhost:9090 을 통해 아래와 같은 화면을 보실수 있습니다.
화면에 보이시는 Expression에 메트릭 값이나 Prometheus용 쿼리를 입력하시면 "Console" 탭에서는 현재 값을, " Graph"탭에서는 특정 기간동안의 그래프를 확인하실수 있습니다. 좀 더 다양한 그래프를 보시려면 다음에 설명하는 Grafana를 이용하시면 됩니다.





Grafana 실행

1) Grafana docker 컨테이너 생성

아래 명령을 통해 Grafana 대시보드의 기본 포트인 3000을 매핑하여 Grafana 컨테이너를 생성합니다. 컨테이너가 생성되면 브라우저에서 http://localhost:3000를 통해 Grafana 화면을 보실수 있습니다.


docker run -d -p 3000:3000 grafana/grafana

2) Grafana 대시보드 가져오기

기본 아이디와 패스워드는 https://hub.docker.com/r/grafana/grafana에서 확인하실수 있습니다. 현재 값은 admin/admin입니다. 아이디와 패스워드를 입력하시면 패스워드 변경창이 실행됩니다. 패스워드를 변경을 하시거나 skip 버튼을 누르시면 아래와 같은 화면을 보실수 있습니다.

Grafana 대시보드를 사용하기 위해 우선 데이터 소스를 설정해야 합니다. 화면에 보이시는 "Add data source"를 클릭하고 "Prometheus"를 선택하고 아래 그림과 같이 Access 타입을 "Browser"로 변경하고 "URL"에 "http://localhost:9090" 을 입력합니다. 일반적인 운영 환경에서는 기본적으로 Access를 "Server"로 사용하여 Grafana에서 Prometheus Server로 직접 연결하는 방식을 사용하셔야 합니다. 만약 Access를 "Server" 타입으로 설정하려면, docker의 네트워크 설정을 통해 Prometheus 서버와 Grafana를 같은 네트워크를 사용하도록 설정해 주셔야 합니다. 하지만 본 글에서는 docker 네트워크 설정을 하지 않았기 때문에 타입을 "Browser"로 설정하여 브라우저에서 Prometheus 서버로 접근하는 방식을 사용합니다. 입력이 완료되면 "Save & Test" 버튼을 클릭하여 Grafana에서 Prometheus 서버로의 접근이 가능한지 확인하시면 됩니다.

"Back" 버튼을 누르시면 아래와 같이 데이터 소스가 추가되신걸 확인하실 수 있습니다.

추가하신 데이터 소소를 이용하여 아래 그림의 + 버튼을 통해 새로운 대시보드를 생성하거나 "import" 메뉴를 통해 기존 대시보드를 가져올수 있습니다. 여기서는 기존의 만들어진 대시보드를 사용하기 위해 "import" 메뉴를 클릭합니다.

"Upload .json File" 버튼을 클릭하신후 github에서 가져온 grafana.json 파일을 선택합니다. 대시보드 이름과 폴더를 선택한 후 "Import" 버튼을 클릭합니다. 아래와 같은 그래프 화면을 보실 수 있습니다. 해당 대시보드는 위의 어플리케이션에서 생성된 메트릭을 다양한 그래프를 사용하여 보여주도록 하였습니다.

각각의 그래프에서 사용된 쿼리는 해당 그래프의 타이틀을 클릭 하신 후 "Edit" 메뉴를 선택하시면 보실 수 있습니다.

이 외에도 Grafana에서는 다양한 쿼리와 그래프 형태를 사용하여 데이터를 보실 수 있습니다. 이전편에 언급해 드렸던 Grafana 샘플(https://play.grafana.org) 페이지를 참고하셔서 여러분만의 다양한 그래프를 만들어 보시기 바랍니다.




맺음말


본 시리즈의 글을 통해 Prometheus와 Grafana, 그리고 이를 Prometheus에 Custom 메트릭을 보내는 방법에 대해 설명하였습니다. 하지만, Prometheus 및 Grafana는 여기서 설명하지 않은 많은 기능들이 있습니다. 예를들어, 운영에 중요한 메트릭 값의 이상증세를 파악하여 경고를 보내주는 Alert 기능(https://prometheus.io/docs/alerting/overview/)도 있습니다. 이런 다양한 기능들은 MSA환경에서 서비스의 이상을 좀 더 빠르게 파악하고 수정할 수 있도록 도움을 줄 것입니다. MSA 환경에서의