Criação de perfis de aplicações Go

Esta página descreve como modificar a sua aplicação Go para capturar dados de criação de perfis e enviar esses dados para o seu projeto do Google Cloud. Google CloudPara ver informações gerais acerca da criação de perfis, consulte o artigo Conceitos de criação de perfis.

Tipos de perfis para o Go:

  • Tempo da CPU
  • Memória
  • Memória dinâmica atribuída
  • Contenção (mutex Go)
  • Threads (Go goroutine)

Versões do idioma Go suportadas:

Versões do agente de criação de perfis suportadas:

  • A versão mais recente do agente é suportada. Geralmente, as versões com mais de um ano não são suportadas. Recomendamos que use a versão do agente lançada mais recentemente.

Sistemas operativos compatíveis:

  • Linux. A criação de perfis de aplicações Go é suportada para kernels Linux cuja biblioteca C padrão é implementada com glibc ou com musl. Para ver informações de configuração específicas dos kernels do Linux Alpine, consulte o artigo Execução no Linux Alpine.

Ambientes suportados:

  • Compute Engine
  • Google Kubernetes Engine (GKE)
  • Ambiente flexível do App Engine
  • Ambiente padrão do App Engine (requer o Go 1.11 ou superior)
  • Fora de Google Cloud (Para obter informações sobre os requisitos de configuração adicionais, consulte o artigo Criar perfis de aplicações em execução fora de Google Cloud.)

Ativar a API Profiler

Antes de usar o agente de criação de perfis, certifique-se de que a API Profiler subjacente está ativada. Pode verificar o estado da API e ativá-la, se necessário, através da CLI do Google Cloud ou da Google Cloud consola:

CLI gcloud

  1. Se ainda não instalou a CLI do Google Cloud na sua estação de trabalho, consulte a documentação da CLI do Google Cloud.

  2. Execute o seguinte comando:

    gcloud services enable cloudprofiler.googleapis.com
    

Para mais informações, consulte gcloud services.

Google Cloud consola

  1. Enable the required API.

    Roles required to enable APIs

    To enable APIs, you need the Service Usage Admin IAM role (roles/serviceusage.serviceUsageAdmin), which contains the serviceusage.services.enable permission. Learn how to grant roles.

    Enable the API

  2. Se for apresentada a mensagem API ativada, significa que a API já está ativada. Caso contrário, clique no botão Ativar.

Conceda a função do IAM à conta de serviço

Se estiver a implementar a sua aplicação em Google Cloud recursos e se estiver a usar a conta de serviço predefinida e não tiver modificado as concessões de funções para essa conta de serviço, pode ignorar esta secção.

Se realizar qualquer uma das seguintes ações, tem de conceder à conta de serviço a função do IAM de agente do Cloud Profiler (roles/cloudprofiler.agent):

  1. Está a usar a conta de serviço predefinida, mas modificou as concessões de funções.
  2. Está a usar uma conta de serviço criada pelo utilizador.
  3. Está a usar a identidade da carga de trabalho. Conceda a função de agente do Cloud Profiler à conta de serviço do Kubernetes.

Pode conceder uma função de IAM a uma conta de serviço através da Google Cloud consola ou da CLI do Google Cloud. Por exemplo, pode usar o comando gcloud projects add-iam-policy-binding:

gcloud projects add-iam-policy-binding GCP_PROJECT_ID \
    --member serviceAccount:MY_SVC_ACCT_ID@GCP_PROJECT_ID.iam.gserviceaccount.com \
    --role roles/cloudprofiler.agent

Antes de usar o comando anterior, substitua o seguinte:

  • GCP_PROJECT_ID: o ID do seu projeto.
  • MY_SVC_ACCT_ID: o nome da sua conta de serviço.

Para ver informações detalhadas, consulte o artigo Faça a gestão do acesso a projetos, pastas e organizações.

Usar o Cloud Profiler

Em todos os ambientes suportados, usa o Profiler ao importar o pacote na sua aplicação e, em seguida, inicializar o Profiler o mais cedo possível na sua aplicação.

Pode ativar a criação de perfis de contenção de Mutex ("Contention" na interface) definindo a opção de configuração MutexProfiling como true.

Para mais informações sobre a API Profiler, incluindo todas as opções de configuração, consulte os documentos da API pública.

Compute Engine

Para o Compute Engine, em profiler.Config, defina Service com um nome para o serviço que está a ser analisado e, opcionalmente, defina ServiceVersion com a versão do serviço:


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

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

func main() {
	cfg := profiler.Config{
		Service:        "myservice",
		ServiceVersion: "1.0.0",
		// ProjectID must be set if not running on GCP.
		// ProjectID: "my-project",

		// For OpenCensus users:
		// To see Profiler agent spans in APM backend,
		// set EnableOCTelemetry to true
		// EnableOCTelemetry: true,
	}

	// Profiler initialization, best done as early as possible.
	if err := profiler.Start(cfg); err != nil {
		// TODO: Handle error.
	}
}

Se tiver dependências no código-fonte que são obtidas manualmente, pode ter de adicionar o seguinte ao script de compilação ou ao Dockerfile:

go get cloud.google.com/go/profiler

GKE

Para o GKE, em profiler.Config, defina Service com um nome para o serviço que está a ser analisado e, opcionalmente, defina ServiceVersion com a versão do serviço:


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

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

func main() {
	cfg := profiler.Config{
		Service:        "myservice",
		ServiceVersion: "1.0.0",
		// ProjectID must be set if not running on GCP.
		// ProjectID: "my-project",

		// For OpenCensus users:
		// To see Profiler agent spans in APM backend,
		// set EnableOCTelemetry to true
		// EnableOCTelemetry: true,
	}

	// Profiler initialization, best done as early as possible.
	if err := profiler.Start(cfg); err != nil {
		// TODO: Handle error.
	}
}

Se tiver dependências no código-fonte que são obtidas manualmente, pode ter de adicionar o seguinte ao script de compilação ou ao Dockerfile:

go get cloud.google.com/go/profiler

App Engine

Para o ambiente flexível do App Engine e o ambiente padrão do App Engine, as adições de código são quase idênticas às do Compute Engine e do GKE. Existe uma exceção. Em ambos os ambientes do App Engine, os parâmetros Service e ServiceVersion são derivados do ambiente, pelo que não tem de os especificar.


// 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.
	}
}

Quando executa a aplicação localmente, defina os parâmetros ProjectID (o ID do seu projeto) e Service em profiler.Config, uma vez que não podem ser derivados de um ambiente local.Google Cloud Não precisa de configurar ServiceVersion.

Se estiver a usar o ambiente padrão do App Engine, consulte o artigo Migrar a sua app para o Go 1.11 para ver informações detalhadas sobre as alterações que pode ter de fazer à sua aplicação. Além disso, tem de usar a versão 226.0.0 ou posterior da CLI Google Cloud. Para atualizar a CLI Google Cloud, execute o seguinte comando:

gcloud components update

Para executar a sua aplicação:

  1. Atualize as dependências:

    go get cloud.google.com/go/profiler
    
  2. Implemente a aplicação no ambiente flexível do App Engine ou no ambiente padrão do App Engine:

    gcloud app deploy [DEPLOYMENT]
    

    em que DEPLOYMENT é o caminho para o ficheiro de configuração. Por exemplo, DEPLOYMENT pode ser main/app.yaml.

Analisar dados

Depois de o Perfilador recolher dados, pode ver e analisar estes dados através da interface do Perfilador.

Na Google Cloud consola, aceda à página Profiler:

Aceda ao Profiler

Também pode encontrar esta página através da barra de pesquisa.

Argumentos de nome e versão do serviço

Quando carrega o agente do Profiler, especifica um argumento service-name e um argumento service-version opcional para o configurar.

O nome do serviço permite que o Profiler recolha dados de criação de perfis para todas as réplicas desse serviço. O serviço de criação de perfis garante uma taxa de recolha de um perfil por minuto, em média, para cada nome de serviço em todas as combinações de versões e zonas de serviço.

Por exemplo, se tiver um serviço com duas versões em execução em réplicas em três zonas, o criador de perfis cria uma média de 6 perfis por minuto para esse serviço.

Se usar nomes de serviços diferentes para as suas réplicas, o serviço é perfilado com mais frequência do que o necessário, com uma sobrecarga correspondentemente mais elevada.

Ao selecionar um nome do serviço:

  • Escolha um nome que represente claramente o serviço na arquitetura da sua aplicação. A escolha do nome do serviço é menos importante se executar apenas um único serviço ou aplicação. É mais importante se a sua aplicação for executada como um conjunto de microsserviços, por exemplo.

  • Certifique-se de que não usa valores específicos do processo, como um ID do processo, na string service-name.

  • A string service-name tem de corresponder a esta expressão regular:

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

Uma boa diretriz é usar uma string estática como imageproc-service como o nome do serviço.

A versão do serviço é opcional. Se especificar a versão do serviço, o Profiler pode agregar informações de criação de perfis de várias instâncias e apresentá-las corretamente. Pode ser usado para marcar diferentes versões dos seus serviços à medida que são implementadas. A IU do Profiler permite-lhe filtrar os dados por versão do serviço. Desta forma, pode comparar o desempenho de versões mais antigas e mais recentes do código.

O valor do argumento service-version é uma string de forma livre, mas os valores deste argumento têm normalmente o aspeto de números de versão, por exemplo, 1.0.0 ou 2.1.2.

Registo do agente

O agente de criação de perfis pode comunicar informações de depuração nos respetivos registos. Por predefinição, o registo do agente está desativado.

Para ativar o registo do agente, defina a opção DebugLogging como true ao iniciar o agente:

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

Resolução de problemas

Esta secção apresenta problemas específicos da criação de perfis de aplicações Go. Consulte a resolução de problemas para obter ajuda com problemas comuns.

Comportamento Causa Solução
Os perfis de tempo da CPU não são recolhidos para aplicações criadas com -buildmode=c-archive. São recolhidos perfis de memória, contenção e threads. Problema do GitHub Por predefinição, a criação de perfis da CPU não está ativada para aplicações Go quando a flag -buildmode é c-archive ou c-shared. Adicione uma chamada a
signal.Notify(make(
chan os.Signal), syscall.SIGPROF)
antes de ligar para profiler.Start.
Resposta ao problema do GitHub.

Execução com o Linux Alpine

O agente de criação de perfis Go para Linux Alpine só é suportado para configurações do Google Kubernetes Engine.

Erro de autenticação

Se usar imagens do Docker executadas com o Linux Alpine (como golang:alpine ou apenas alpine), pode ver o seguinte erro de autenticação:

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

Tenha em atenção que, para ver o erro, tem de ter o registo do agente ativado. Por predefinição, o agente para Go não produz mensagens de registo.

O erro indica que as imagens do Docker com o Linux Alpine não têm os certificados SSL de raiz instalados por predefinição. Esses certificados são necessários para que o agente de criação de perfis comunique com a API Profiler. Para resolver este erro, adicione o seguinte comando apk ao seu Dockerfile:

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

Em seguida, tem de recriar e voltar a implementar a aplicação.

O que se segue?