Como recuperar credenciais/segredos do Secret Manager com o Spring Boot

1. Visão geral

Secrets como senhas e chaves de API são informações sensíveis que precisam ser guardadas em um armazenamento seguro e criptografado, com acesso controlado e auditáveis. Alguns sistemas optam por usar o Vault para armazenar essas chaves secretas. No Google Cloud, é possível usar o Secret Manager, um serviço gerenciado, para armazenar secrets com segurança e controlar o acesso a secrets individuais usando o IAM.

No Spring Boot, você pode usar o Spring Cloud GCP para acessar facilmente esses segredos, referindo-se a eles como qualquer outra propriedade do Spring.

Neste codelab, você vai armazenar um secret no Secret Manager, criar microsserviços simples do Spring Boot e recuperá-lo.

O que você vai aprender

  • Como criar um aplicativo Java do Spring Boot e configurar o Secret Manager.

O que é necessário

  • Um projeto do Google Cloud
  • Um navegador, como o Chrome ou o Firefox
  • Conhecer os editores de texto padrão do Linux, como vim, emacs ou nano

Como você vai usar este tutorial?

Apenas leitura Leitura e exercícios

Como você classificaria sua experiência com a criação de apps da Web HTML/CSS?

Iniciante Intermediário Proficiente

Como você classificaria sua experiência de uso dos serviços do Google Cloud?

Iniciante Intermediário Proficiente

2. Configuração e requisitos

Configuração de ambiente autoguiada

  1. Faça login no Console do Cloud e crie um novo projeto ou reutilize um existente. Crie uma se você ainda não tiver uma conta do Gmail ou do G Suite.

dMbN6g9RawQj_VXCSYpdYncY-DbaRzr2GbnwoV7jFf1u3avxJtmGPmKpMYgiaMH-qu80a_NJ9p2IIXFppYk8x3wyymZXavjglNLJJhuXieCem56H30hwXtd8PvXGpXJO9gEUDu3cZw

ci9Oe6PgnbNuSYlMyvbXF1JdQyiHoEgnhl4PlV_MFagm2ppzhueRkqX4eLjJllZco_2zCp0V0bpTupUSKji9KkQyWqj11pqit1K1faS1V6aFxLGQdkuzGp4rsQTan7F01iePL5DtqQ

8-tA_Lheyo8SscAVKrGii2coplQp2_D1Iosb2ViABY0UUO1A8cimXUu6Wf1R9zJIRExL5OB2j946aIiFtyKTzxDcNnuznmR45vZ2HMoK3o67jxuoUJCAnqvEX6NgPGFjCVNgASc-lg

Lembre-se do código do projeto, um nome exclusivo em todos os projetos do Google Cloud. O nome acima já foi escolhido e não servirá para você. Faremos referência a ele mais adiante neste codelab como PROJECT_ID.

  1. Em seguida, será necessário ativar o faturamento no Console do Cloud para usar os recursos do Google Cloud.

A execução deste codelab não será muito cara, se for o caso. Siga todas as instruções na seção "Limpeza", que orienta você sobre como encerrar recursos para não incorrer em cobranças além deste tutorial. Novos usuários do Google Cloud estão qualificados para o programa de US$ 300 de avaliação sem custos.

Google Cloud Shell

Embora os serviços do Google Cloud possam ser operados remotamente do seu laptop, neste codelab vamos usar o Google Cloud Shell, um ambiente de linha de comando executado no Cloud.

Ativar o Cloud Shell

  1. No Console do Cloud, clique em Ativar o Cloud ShellH7JlbhKGHITmsxhQIcLwoe5HXZMhDlYue4K-SPszMxUxDjIeWfOHBfxDHYpmLQTzUmQ7Xx8o6OJUlANnQF0iBuUyfp1RzVad_4nCa0Zz5LtwBlUZFXFCWFrmrWZLqg1MkZz2LdgUDQ.

zlNW0HehB_AFW1qZ4AyebSQUdWm95n7TbnOr7UVm3j9dFcg6oWApJRlC0jnU1Mvb-IQp-trP1Px8xKNwt6o3pP6fyih947sEhOFI4IRF0W7WZk6hFqZDUGXQQXrw21GuMm2ecHrbzQ

Se você nunca tiver iniciado o Cloud Shell, verá uma tela intermediária (abaixo da dobra) com a descrição do que ele é. Se esse for o caso, clique em Continuar e você não o verá novamente. Esta é uma tela única:

kEPbNAo_w5C_pi9QvhFwWwky1cX8hr_xEMGWySNIoMCdi-Djx9AQRqWn-__DmEpC7vKgUtl-feTcv-wBxJ8NwzzAp7mY65-fi2LJo4twUoewT1SUjd6Y3h81RG3rKIkqhoVlFR-G7w

Leva apenas alguns instantes para provisionar e se conectar ao Cloud Shell.

pTv5mEKzWMWp5VBrg2eGcuRPv9dLInPToS-mohlrqDASyYGWnZ_SwE-MzOWHe76ZdCSmw0kgWogSJv27lrQE8pvA5OD6P1I47nz8vrAdK7yR1NseZKJvcxAZrPb8wRxoqyTpD-gbhA

Essa máquina virtual contém todas as ferramentas de desenvolvimento necessárias. Ela oferece um diretório principal persistente de 5 GB, além de ser executada no Google Cloud. Isso aprimora o desempenho e a autenticação da rede. Praticamente todo o seu trabalho neste codelab pode ser feito em um navegador ou no seu Chromebook.

Depois de se conectar ao Cloud Shell, você já estará autenticado e o projeto já estará configurado com seu ID do projeto.

  1. Execute o seguinte comando no Cloud Shell para confirmar que você está autenticado:
gcloud auth list

Resposta ao comando

 Credentialed Accounts
ACTIVE  ACCOUNT
*       <my_account>@<my_domain.com>

To set the active account, run:
    $ gcloud config set account `ACCOUNT`
gcloud config list project

Resposta ao comando

[core]
project = <PROJECT_ID>

Se o projeto não estiver configurado, configure-o usando este comando:

gcloud config set project <PROJECT_ID>

Resposta ao comando

Updated property [core/project].

3. Configurar um secret

Para usar o Secret Manager, primeiro ative a API:

$ gcloud services enable secretmanager.googleapis.com

Em seguida, crie um secret chamado greeting, com o valor Hello:

$ echo -n "Hello" | \
 gcloud secrets create greeting \
 --data-file=-

Esse comando usa STDIN para fornecer o valor à linha de comando. No entanto, também é possível simplesmente colocar o valor do secret em um arquivo e especificar o nome do arquivo para o argumento --data-file.

É possível listar todos os secrets usando a CLI gcloud:

$ gcloud secrets list

4. Criar um novo serviço REST do Spring Boot

Depois que o Cloud Shell for iniciado, você poderá usar a linha de comando para gerar um novo aplicativo Spring Boot com o Spring Initializr:

$ curl https://start.spring.io/starter.tgz -d packaging=jar \
  -d dependencies=web,cloud-gcp \
  -d bootVersion=3.0.6 \
  -d type=maven-project \
  -d baseDir=hello-secret-manager | tar -xzvf - \
  && cd hello-secret-manager

No pom.xml, adicione a dependência inicial do Spring Cloud GCP:

pom.xml

<project>
  ...

  <dependencies>
    ...
    <!-- Add Secret Manager Starter -->
    <dependency>
      <groupId>com.google.cloud</groupId>
      <artifactId>spring-cloud-gcp-starter-secretmanager</artifactId>
    </dependency>
  </dependencies>

  ...
</project>

No arquivo src/main/resources/application.properties, adicione a seguinte configuração para ativar a API Spring Boot Config Data:

spring.config.import=sm://

Isso vai configurar uma origem da propriedade do Spring, para que você possa fazer referência aos secrets usando um valor de propriedade, com o prefixo sm://, por exemplo, sm://greeting.

Consulte a documentação do Secret Manager do GCP do Spring Cloud para mais detalhes sobre o formato da propriedade. O requisito application.properties é novo no Spring Cloud GCP 4.x. Leia mais detalhes no guia de migração.

Crie um novo controlador REST adicionando um novo arquivo de classe:

src/main/java/com/example/demo/HelloSecretController.java

package com.example.demo;

import org.springframework.web.bind.annotation.GetMapping;
import org.springframework.web.bind.annotation.RestController;

@RestController
public class HelloSecretController {
  String greeting = "Hi";

  @GetMapping("/")
  public String hello() {
    return greeting + " World!";
  }
}

É possível iniciar o aplicativo Spring Boot normalmente com o plug-in Spring Boot.

Verifique se JAVA_HOME está definido como a versão correta do JDK:

$ export JAVA_HOME=/usr/lib/jvm/java-17-openjdk-amd64/

Vamos pular os testes deste laboratório e iniciar o aplicativo:

$ ./mvnw -DskipTests spring-boot:run

Depois que o aplicativo for iniciado, clique no ícone de Visualização da Web e18df08334f0d809.png na barra de ferramentas do Cloud Shell e selecione Visualizar na porta 8080.

Após uma breve espera, você verá o resultado:

1e9a7884ff113c14.png

5. Recuperar um secret

É possível usar a anotação @Value para se referir à propriedade do secret usando o prefixo sm://.

Na classe HelloSecretController, injete o valor greeting usando a anotação:

src/main/java/com/example/demo/HelloSecretController.java

import org.springframework.beans.factory.annotation.Value;

...

@RestController
public class HelloSecretController {
  @Value("${sm://greeting}")
  String greeting;

  ...
}

É possível iniciar o aplicativo Spring Boot normalmente com o plug-in Spring Boot. Vamos pular os testes deste laboratório:

$ ./mvnw -DskipTests spring-boot:run

Assim que o aplicativo for iniciado, clique no ícone "Visualização da Web" e18df08334f0d809.png na barra de ferramentas do Cloud Shell e selecione Visualizar na porta 8080.

Após uma breve espera, você verá o resultado:

Captura de tela do aplicativo em execução, mostrando &quot;Hello World!&quot;

Também é possível mapear o valor para uma propriedade em application.properties:

src/main/resources/application.properties

greeting=${sm://greeting}

No HelloSecretController, é possível fazer referência a este nome de propriedade mais genérico em vez de um nome do Secret Manager:

src/main/java/com/example/demo/HelloSecretController.java

@RestController
public class HelloSecretController {
  @Value("${greeting}")
  String greeting;
  ...
}

É possível iniciar o aplicativo Spring Boot normalmente com o plug-in Spring Boot. Vamos pular os testes deste laboratório:

$ ./mvnw -DskipTests spring-boot:run

Depois que o aplicativo for iniciado, clique no ícone de Visualização da Web Ícone de visualização na Web na barra de ferramentas do Cloud Shell e selecione Visualizar na porta 8080.

Como atualizar o valor do secret

Com a sintaxe curta sm://greeting, você usa automaticamente a versão mais recente do secret. Ao criar uma nova versão do secret, você pode atualizar seu aplicativo sem alterar seu código.

Atualize o valor do secret adicionando uma nova versão:

$ echo -n "Greetings" |
 gcloud secrets versions add greeting \
 --data-file=-

Reinicie o aplicativo e verifique se a nova versão do secret está sendo retornada.

Captura de tela do aplicativo em execução, mostrando a mensagem &quot;Greeings World!&quot;

Expansão desse conceito

Essa técnica é útil especialmente se você usar diferentes perfis de aplicativo do Spring Boot. Por exemplo, é possível criar secrets como greeting-dev, greeting-staging e greeting-prod. Em cada perfil, faça o mapeamento para as saudações certas.

Crie um secret greeting-prod:

$ echo -n "Hola" | \
 gcloud secrets create greeting-prod \
 --data-file=- --replication-policy=automatic

Crie um arquivo application-prod.properties:

src/main/resources/application-prod.properties

greeting=${sm://greeting-prod}

É possível iniciar o aplicativo Spring Boot normalmente com o plug-in Spring Boot, mas com o perfil prod. Vamos pular os testes deste laboratório:

$ ./mvnw -DskipTests spring-boot:run -Dspring-boot.run.profiles=prod

Assim que o aplicativo for iniciado, clique no ícone "Visualização da Web" Ícone de visualização da Web na barra de ferramentas do Cloud Shell e selecione Visualizar na porta 8080.

Após uma breve espera, você verá o resultado:

Captura de tela do aplicativo em execução, mostrando a mensagem &quot;Hola World!&quot;

6. Resumo

Neste laboratório, você criou um serviço que pode ser configurado com secrets armazenados no Secret Manager com os nomes de propriedades do Spring com o prefixo sm:// e injetando o valor do arquivo applications.properties e das anotações @Value.

7. Parabéns!

Você aprendeu a usar a API Secret Manager no Java.

Saiba mais

Licença

Este conteúdo está sob a licença Atribuição 2.0 Genérica da Creative Commons.