Go 애플리케이션 프로파일링

이 페이지에서는 프로파일링 데이터를 캡처하고 캡처된 데이터를 Google Cloud Platform(GCP) 프로젝트로 전송하도록 Go 애플리케이션을 수정하는 방법을 설명합니다. 프로파일링에 대한 일반 정보는 프로파일링 개념을 참조하세요.

Go의 프로필 유형:

  • CPU 시간
  • 할당된 힙
  • 경합(Go 뮤텍스)
  • 스레드(Go goroutine)

지원되는 Go 언어 버전:

  • 달리 명시하지 않는 한 공식적으로 유지되는 모든 Go 출시 버전. 자세한 내용은 Go 언어 출시 정책을 참조하세요.

지원되는 운영체제:

  • Linux. Go 애플리케이션 프로파일링은 표준 C 라이브러리가 glibc 또는 musl로 구현된 Linux 커널에서 지원됩니다. Linux Alpine 커널의 구성 정보는 Linux Alpine에서 실행을 참조하세요.

지원되는 환경:

Profiler API 사용 설정

프로파일링 에이전트를 사용하기 전에 기본 Profiler API가 사용 설정되어 있는지 확인하세요. API의 상태를 확인하고 필요할 경우 Cloud SDK gcloud 명령줄 도구 또는 Cloud Console을 사용하여 사용 설정할 수 있습니다.

Cloud SDK

  1. 워크스테이션에 Cloud SDK를 아직 설치하지 않은 경우 Google Cloud SDK를 참조합니다.

  2. 다음 명령어를 실행합니다.

    gcloud services enable cloudprofiler.googleapis.com
    

자세한 내용은 gcloud services를 참조하세요.

Cloud Console

  1. API 및 서비스 대시보드로 이동합니다.

    API 및 서비스로 이동

  2. API에 액세스하는 데 사용할 프로젝트를 선택합니다.

  3. API 및 서비스 추가 버튼을 클릭합니다.

    API 및 서비스 추가

  4. Profiler API를 검색합니다.

  5. 검색결과에서 Stackdriver Profiler API를 선택합니다.

  6. API 사용 설정됨이 표시된다면 API가 이미 사용 설정되어 있는 것입니다. 그렇지 않다면 사용 설정 버튼을 클릭하세요.

Stackdriver Profiler 사용

지원되는 모든 환경에서 애플리케이션의 패키지를 가져온 후 애플리케이션에서 가능한 한 빨리 Profiler를 초기화하여 사용합니다.

MutexProfiling 구성 옵션을 true로 설정하여 뮤텍스 경합 프로파일링(인터페이스의 '경합')을 사용 설정할 수 있습니다.

Profiler API에 대한 자세한 내용(모든 구성 옵션 포함)은 공개 API 문서를 참조하세요.

Compute Engine

Compute Engine의 profiler.Config에서 프로파일링할 서비스 이름으로 Service를 설정하고, 원하는 경우 서비스 버전으로 ServiceVersion을 설정합니다.


// snippets is an example of starting cloud.google.com/go/profiler.
package main

import (
	"cloud.google.com/go/profiler"
)

func main() {
	// Profiler initialization, best done as early as possible.
	if err := profiler.Start(profiler.Config{
		Service:        "myservice",
		ServiceVersion: "1.0.0",
		// ProjectID must be set if not running on GCP.
		// ProjectID: "my-project",
	}); err != nil {
		// TODO: Handle error.
	}
}

소스 코드에 수동으로 가져오는 종속 항목이 있는 경우 빌드 스크립트 또는 Dockerfile에 다음 줄을 추가해야 할 수도 있습니다.

go get -u cloud.google.com/go/profiler

GKE

GKE의 profiler.Config에서 프로파일링할 서비스 이름으로 Service를 설정하고, 원하는 경우 서비스 버전으로 ServiceVersion을 설정합니다.


// snippets is an example of starting cloud.google.com/go/profiler.
package main

import (
	"cloud.google.com/go/profiler"
)

func main() {
	// Profiler initialization, best done as early as possible.
	if err := profiler.Start(profiler.Config{
		Service:        "myservice",
		ServiceVersion: "1.0.0",
		// ProjectID must be set if not running on GCP.
		// ProjectID: "my-project",
	}); err != nil {
		// TODO: Handle error.
	}
}

소스 코드에 수동으로 가져오는 종속 항목이 있는 경우 빌드 스크립트 또는 Dockerfile에 다음 줄을 추가해야 할 수도 있습니다.

go get -u cloud.google.com/go/profiler

App Engine

App Engine 가변형 환경과 App Engine 표준 환경의 코드 추가 형태는 Compute Engine 및 GKE의 코드 추가 형태와 거의 동일하지만 한 가지 예외가 있습니다. 두 App Engine 환경 모두에서 ServiceServiceVersion 매개변수가 환경에서 파생되므로 별도로 지정할 필요가 없습니다.


// appengine is an example of starting cloud.google.com/go/profiler on
// App Engine.
package main

import (
	"cloud.google.com/go/profiler"
)

func main() {
	// Profiler initialization, best done as early as possible.
	if err := profiler.Start(profiler.Config{
		// Service and ServiceVersion can be automatically inferred when running
		// on App Engine.
		// ProjectID must be set if not running on GCP.
		// ProjectID: "my-project",
	}); err != nil {
		// TODO: Handle error.
	}
}

하지만 애플리케이션을 로컬에서 실행하는 경우에는 ProjectID(GCP 프로젝트의 ID) 및 Service 매개변수(profiler.Config에 포함)가 로컬 환경에서 파생될 수 없으므로 별도로 설정합니다. ServiceVersion은 설정할 필요가 없습니다.

App Engine 표준 환경을 사용 중인 경우 Go 1.11로 앱 이전에서 애플리케이션에 적용해야 하는 변경사항에 대한 자세한 내용을 참조하세요. 또한 Cloud SDK 버전 226.0.0 이상을 사용해야 합니다. Cloud SDK를 업데이트하려면 다음 명령어를 실행하세요.

    gcloud components update

애플리케이션을 실행하려면 다음 안내를 따르세요.

  1. 종속 항목을 업데이트합니다.

    go get -u cloud.google.com/go/profiler
    
  2. App Engine 가변형 환경 또는 App Engine 표준 환경에 애플리케이션을 배포합니다.

    gcloud app deploy [DEPLOYMENT]
    

    여기서 DEPLOYMENT는 구성 파일의 경로입니다. 예를 들어 DEPLOYMENTmain/app.yaml일 수 있습니다.

데이터 분석

Profiler가 데이터를 수집하면 개발자가 Profiler 인터페이스를 사용하여 이 데이터를 보고 분석할 수 있습니다. 이 인터페이스를 사용하기 시작하려면 Profiler 인터페이스 열기를 참조하세요.

서비스 이름 및 버전 인수

Profiler 에이전트를 로드할 때는 서비스 이름 인수와 선택적 서비스 버전 인수를 지정하여 구성합니다.

서비스 이름은 Profiler가 해당 서비스의 모든 복제본에 대한 프로파일링 데이터를 수집할 수 있게 해줍니다. 프로파일러 서비스는 각 서비스 버전 및 영역(zone)의 조합에서 각 서비스 이름에 평균적으로 프로필이 1분에 하나씩 수집되도록 보장합니다.

예를 들어 두 버전이 3개 영역(zone)의 복제본에서 실행 중인 서비스가 있다면 프로파일러가 해당 서비스에 대한 프로필을 평균적으로 1분에 6개씩 만듭니다.

복제본에 서로 다른 서비스 이름을 사용하면 서비스가 불필요하게 자주 프로파일링되므로 오버헤드도 높아집니다.

서비스 이름을 선택할 때 다음에 유의하세요.

  • 애플리케이션 아키텍처에서 서비스를 분명히 나타내는 이름을 선택합니다. 단일 서비스 또는 애플리케이션만 실행하는 경우에는 서비스 이름 선택이 크게 중요하지 않습니다. 하지만 애플리케이션이 마이크로 서비스 집합으로 실행되는 경우와 같은 사례에서는 서비스 이름 선택이 중요합니다.

  • 서비스 이름 문자열에 프로세스 ID와 같은 프로세스 관련 값을 사용하지 않도록 합니다.

  • 서비스 이름 문자열은 다음과 같은 정규 표현식과 일치해야 합니다.

    ^[a-z]([-a-z0-9_.]{0,253}[a-z0-9])?$

imageproc-service와 같은 정적 문자열을 서비스 이름으로 사용하는 것이 좋습니다.

서비스 버전은 선택사항입니다. 서비스 버전을 지정하면 Profiler가 여러 인스턴스의 프로파일링 정보를 집계하여 올바르게 표시할 수 있습니다. 배포된 서비스의 여러 버전을 표시할 때 서비스 버전을 사용할 수 있습니다. Profiler UI를 사용하면 서비스 버전별로 데이터를 필터링할 수 있습니다. 그러면 이전 버전과 새로운 버전의 코드 성능을 비교할 수 있습니다.

서비스 버전 인수의 값은 자유 형식의 문자열이지만 이 인수의 값은 일반적으로 버전 번호와 유사합니다(예: 1.0.0 또는 2.1.2).

에이전트 로깅

프로파일링 에이전트는 로그의 디버그 정보를 보고할 수 있습니다. 기본적으로 에이전트 로깅은 사용 중지되어 있습니다.

에이전트 로깅을 사용 설정하려면 에이전트를 시작할 때 DebugLogging 옵션을 true로 설정합니다.

profiler.Start(profiler.Config{..., DebugLogging: true});

Linux Alpine으로 실행

Linux Alpine으로 실행되는 Docker 이미지(예: golang:alpine 또는 alpine)를 사용하는 경우 다음과 같은 인증 오류가 표시될 수 있습니다.

connection error: desc = "transport: authentication handshake failed: x509: failed to load system roots and no roots provided"

이 오류를 확인하려면 에이전트 로깅을 사용 설정해야 합니다. 기본적으로 Go 에이전트는 로그 메시지를 출력하지 않습니다.

이 오류는 Linux Alpine을 사용하는 Docker 이미지에 루트 SSL 인증서가 기본적으로 설치되어 있지 않음을 나타냅니다. 이러한 인증서는 프로파일링 에이전트가 Profiler API와 통신하는 데 필요합니다. 이 오류를 해결하려면 Dockerfile에 다음 apk 명령어를 추가하세요.

FROM alpine
...
RUN apk add --no-cache ca-certificates

그런 다음 애플리케이션을 다시 빌드하고 다시 배포해야 합니다.

다음 단계

Profiler 그래프 및 컨트롤에 대해 알아보려면 Stackdriver Profiler 인터페이스 사용으로 이동하세요. 고급 정보는 다음을 참조하세요.

이 페이지가 도움이 되었나요? 평가를 부탁드립니다.

다음에 대한 의견 보내기...

Stackdriver Profiler