1. Visão geral
Esta série de codelabs (tutoriais práticos e autoguiados) destina-se a ajudar os desenvolvedores Java do Google App Engine (Padrão) a modernizar os aplicativos por meio de uma série de migrações. Seguindo estas etapas, você pode atualizar seu app para que ele seja mais portátil e decidir colocá-lo em contêineres para o Cloud Run, o serviço irmão de hospedagem de contêiner do Google Cloud no App Engine e em outros serviços de hospedagem de contêiner.
Neste tutorial, você aprende a colocar um app do App Engine em contêiner para implantação no serviço totalmente gerenciado do Cloud Run usando o Jib. Com o Jib, é possível criar imagens Docker, uma plataforma conhecida no setor de desenvolvimento, envio e execução de aplicativos em contêineres.
Além de ensinar as etapas necessárias para migrar do App Engine para o Cloud Run, você também vai aprender a fazer upgrade de um app do App Engine em Java 8 para o Java 17.
Se o aplicativo usar muito os serviços agrupados legados do App Engine ou outros recursos do App Engine, recomendamos migrar desses serviços agrupados ou substituir esses recursos antes de passar para o Cloud Run. Se você precisar de mais tempo para investigar as opções de migração ou quiser continuar usando os serviços incluídos legados por enquanto, acesse os serviços incluídos do App Engine para Java 11/17 ao fazer upgrade para um ambiente de execução mais recente. Quando seu app estiver mais portátil, volte a este codelab para aprender a aplicar as instruções ao seu app.
Você vai aprender a
- Usar o Cloud Shell
- Ative as APIs Cloud Run, Artifact Registry e Cloud Build.
- Conteinerizar seu app usando o Jib e o Cloud Build
- Implante imagens de contêiner no Cloud Run
O que é necessário
- Um projeto do Google Cloud Platform com uma conta de faturamento do GCP ativa e o App Engine ativado
- Conhecimento prático de comandos comuns do Linux
- Conhecimento básico sobre desenvolvimento e implantação de apps do App Engine
- Um app servlet Java 8 que você quer migrar para o Java 17 e implantar no Cloud Run. Pode ser um app no App Engine ou apenas a origem.
Pesquisa
Como você vai usar este tutorial?
Como você classificaria sua experiência com Java?
Como você classificaria sua experiência de uso dos serviços do Google Cloud?
2. Contexto
Os sistemas de plataforma como serviço (PaaS), como o App Engine e o Cloud Functions, oferecem muitas conveniências para sua equipe e aplicativo, como permitir que SysAdmins e Devops se concentrem na criação de soluções. Com plataformas sem servidor, seu app pode ser escalonado automaticamente de acordo com a necessidade, reduzir escala vertical para zero com o faturamento por uso para ajudar a controlar custos e usar uma variedade de linguagens de desenvolvimento comuns.
No entanto, a flexibilidade dos contêineres também é atraente. Com a capacidade de escolher qualquer linguagem, biblioteca e binário, os contêineres oferecem o melhor dos dois mundos: a conveniência da computação sem servidor e a flexibilidade dos contêineres. É disso que se trata o Cloud Run.
O aprendizado deste codelab não está no escopo deste codelab coberto pela documentação do Cloud Run. O objetivo aqui é você se familiarizar com a colocação do aplicativo do App Engine em um contêiner para o Cloud Run (ou outros serviços hospedados em contêineres). Há algumas coisas que você precisa saber antes de avançar, principalmente que a experiência do usuário será um pouco diferente.
Neste codelab, você vai aprender a criar e implantar contêineres. Você vai aprender a:
- Contentorização do app com o Jib
- Migrar da configuração do App Engine
- e, opcionalmente, defina etapas de build para o Cloud Build.
Isso vai envolver a remoção de alguns recursos específicos do App Engine. Se preferir não seguir esse caminho, você ainda pode fazer upgrade para um ambiente de execução do Java 11/17 enquanto mantém seus apps no App Engine.
3. Configuração/Pré-trabalho
1. Configurar projeto
Neste tutorial, você vai usar um app de exemplo do repositório appengine-java-migration-samples em um projeto novo. Verifique se o projeto tem uma conta de faturamento ativa.
Se você pretende mover um app do App Engine para o Cloud Run, use esse app para acompanhar o tutorial.
Execute o comando a seguir para ativar as APIs necessárias para seu projeto:
gcloud services enable artifactregistry.googleapis.com cloudbuild.googleapis.com run.googleapis.com
2. Receber app de exemplo do valor de referência
Clone o app de exemplo na sua máquina ou no Cloud Shell e navegue até a pasta baseline.
A amostra é um app do Datastore baseado em servlet Java 8 destinado à implantação no App Engine. Siga as instruções no README para preparar o app para implantação no App Engine.
3. (Opcional) Implantar aplicativo de referência
O seguinte só é necessário se você quiser confirmar que o app funciona no App Engine antes de migrar para o Cloud Run.
Consulte as etapas em README.md:
- Instalar/relembrar a CLI
gcloud - Inicialize a CLI gcloud para seu projeto com
gcloud init - Crie o projeto do App Engine com
gcloud app create - Implantar o app de exemplo no App Engine
./mvnw package appengine:deploy -Dapp.projectId=$PROJECT_ID
- Confirmar se o aplicativo é executado no App Engine sem problemas
4. Criar um repositório do Artifact Registry
Depois de contêinerizar o app, você vai precisar de um lugar para enviar e armazenar as imagens. A maneira recomendada de fazer isso no Google Cloud é com o Artifact Registry.
Crie o repositório chamado migration com a gcloud da seguinte maneira:
gcloud artifacts repositories create migration --repository-format=docker \
--description="Docker repository for the migrated app" \
--location="northamerica-northeast1"
Este repositório usa o tipo de formato docker, mas há vários tipos de repositório disponíveis.
Neste ponto, você tem o app do App Engine de base, e o projeto na nuvem do Google Cloud está preparado para migrá-lo para o Cloud Run.
4. Modificar arquivos do aplicativo
Nos casos em que seu app usa muito os serviços incluídos legados, a configuração ou outros recursos exclusivos do App Engine, recomendamos continuar acessando esses serviços ao fazer upgrade para o novo ambiente de execução. Este codelab demonstra um caminho de migração para aplicativos que já usam serviços independentes ou podem ser refatorados para isso.
1. Fazer upgrade para o Java 17
Se o app estiver no Java 8, considere fazer upgrade para um candidato a LTS mais recente, como 11 ou 17, para acompanhar as atualizações de segurança e ter acesso a novos recursos de linguagem.
Comece atualizando as propriedades em pom.xml para incluir o seguinte:
<properties>
<java.version>17</java.version>
<maven.compiler.source>17</maven.compiler.source>
<maven.compiler.target>17</maven.compiler.target>
</properties>
Isso vai definir a versão do projeto como 17, informar ao plug-in do compilador que você quer acesso aos recursos da linguagem Java 17 e que as classes compiladas sejam compatíveis com a JVM do Java 17.
2. Incluir um servidor da Web
Há várias diferenças entre o App Engine e o Cloud Run que precisam ser consideradas ao migrar entre eles. Uma diferença é que, enquanto o ambiente de execução do Java 8 do App Engine fornecia e gerenciava um servidor Jetty para os apps hospedados, o Cloud Run não faz isso. Vamos usar o Spring Boot para fornecer um servidor da Web e um contêiner de servlet.
Adicione as seguintes dependências:
<dependencies>
<!-- ... -->
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-web</artifactId>
<version>2.6.6</version>
<exclusions>
<!-- Exclude the Tomcat dependency -->
<exclusion>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-tomcat</artifactId>
</exclusion>
</exclusions>
</dependency>
<!-- Use Jetty instead -->
<dependency>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-starter-jetty</artifactId>
<version>2.6.6</version>
</dependency>
<!-- ... -->
</dependencies>
O Spring Boot incorpora um servidor Tomcat por padrão, mas este exemplo vai excluir esse artefato e usar o Jetty para minimizar as diferenças no comportamento padrão após a migração. Também é possível configurar a versão do Jetty para corresponder à fornecida pelo App Engine.
<properties>
<java.version>17</java.version>
<maven.compiler.source>17</maven.compiler.source>
<maven.compiler.target>17</maven.compiler.target>
<jetty.version>9.4.46.v20220331</jetty.version>
</properties>
3. Configuração do Spring Boot
Embora o Spring Boot possa reutilizar seus servlets sem modificação, ele exige alguma configuração para capacidade de descoberta.
Crie a seguinte classe MigratedServletApplication.java no pacote com.example.appengine:
package com.example.appengine;
import org.springframework.boot.SpringApplication;
import org.springframework.boot.autoconfigure.EnableAutoConfiguration;
import org.springframework.boot.autoconfigure.SpringBootApplication;
import org.springframework.boot.web.servlet.ServletComponentScan;
@ServletComponentScan
@SpringBootApplication
@EnableAutoConfiguration
public class MigratedServletApplication {
public static void main(String[] args) {
SpringApplication.run(MigratedServletApplication.class, args);
}
}
Isso inclui a anotação @ServletComponentScan, que vai procurar (no pacote atual por padrão) qualquer @WebServlets e disponibilizá-los conforme o esperado.
4. Como empacotar o app como um JAR
Embora seja possível conteinerizar seu app com o Jib começando com um war, fica mais fácil se você empacotar o app como um JAR executável. Isso não exige muita configuração, principalmente para projetos que usam o Maven como ferramenta de build, já que o pacote jar é o comportamento padrão.
Remova a tag packaging no arquivo pom.xml:
<packaging>war</packaging>
Em seguida, adicione o spring-boot-maven-plugin:
<plugins>
<!-- ... -->
<plugin>
<groupId>org.springframework.boot</groupId>
<artifactId>spring-boot-maven-plugin</artifactId>
<version>2.6.6</version>
</plugin>
<!-- ... -->
</plugins>
5. Migrar da configuração, dos serviços e das dependências do App Engine
Como mencionado no início do codelab, o Cloud Run e o App Engine foram projetados para oferecer experiências de usuário diferentes. Alguns recursos oferecidos pelo App Engine, como os serviços Cron e Task Queue, precisam ser recriados manualmente e serão abordados com mais detalhes em módulos posteriores.
O app de exemplo não usa serviços agrupados legados, mas os usuários que têm apps que usam podem consultar os seguintes guias:
- Migrar de serviços agrupados para encontrar serviços independentes adequados.
- Migrar arquivos de configuração XML para YAML, para usuários que migram para os ambientes de execução Java 11/17 sem sair do App Engine.
Como você vai implantar no Cloud Run a partir de agora, o appengine-maven-plugin pode ser removido:
<plugin>
<groupId>com.google.cloud.tools</groupId>
<artifactId>appengine-maven-plugin</artifactId>
<version>2.4.1</version>
<configuration>
<!-- can be set w/ -DprojectId=myProjectId on command line -->
<projectId>${app.projectId}</projectId>
<!-- set the GAE version or use "GCLOUD_CONFIG" for an autogenerated GAE version -->
<version>GCLOUD_CONFIG</version>
</configuration>
</plugin>
5. Contentorização do aplicativo
Neste ponto, você pode implantar manualmente o app no Cloud Run diretamente do código-fonte. Essa é uma excelente opção que usa o Cloud Build nos bastidores para oferecer uma experiência de implantação sem intervenção. Vamos abordar implantações de origem com mais detalhes em módulos posteriores.
Se você precisar de mais controle sobre a implantação do app, defina um arquivo cloudbuild.yaml que descreva explicitamente as etapas de build pretendidas:
1. Definir um arquivo cloudbuild.yaml
Crie o seguinte arquivo cloudbuild.yaml no mesmo nível do pom.xml:
steps:
# Test your build
- name: maven:eclipse-temurin
entrypoint: mvn
args: ["test"]
# Build with Jib
- name: maven:eclipse-temurin
entrypoint: mvn
args: [ "compile", "com.google.cloud.tools:jib-maven-plugin:3.2.1:build", "-Dimage=northamerica-northeast1-docker.pkg.dev/PROJECT_ID/migration/visitors:jib"]
# Deploy to Cloud Run
- name: 'gcr.io/google.com/cloudsdktool/cloud-sdk'
entrypoint: gcloud
args: [ 'run', 'deploy', 'visitors', '--image', 'northamerica-northeast1-docker.pkg.dev/PROJECT_ID/migration/visitors:jib', '--region', 'northamerica-northeast1', '--allow-unauthenticated']
Depois que instruirmos o Cloud Build a seguir essas etapas, ele vai:
- Executar testes com
./mvnw test - Crie, envie e marque sua imagem para o Artifact Registry com o Jib.
- Implantar a imagem no Cloud Run com
gcloud run deploy
‘visitors' é fornecido ao Cloud Run como o nome de serviço desejado. A flag –allow-unauthenticated permite que os usuários acessem o web app sem precisar de autenticação. Substitua PROJECT_ID pelo ID do seu projeto no arquivo cloudbuild.yaml .
Em seguida, adicione as seguintes vinculações de política do IAM para permitir que a conta de serviço do Cloud Build acesse o Artifact Registry:
export PROJECT_ID=$(gcloud config list --format 'value(core.project)')
export PROJECT_NUMBER=$(gcloud projects describe $PROJECT_ID --format="value(projectNumber)" )
gcloud projects add-iam-policy-binding $PROJECT_ID \
--member=serviceAccount:$PROJECT_NUMBER@cloudbuild.gserviceaccount.com \
--role=roles/run.admin \
--project=$PROJECT_ID
gcloud iam service-accounts add-iam-policy-binding $PROJECT_NUMBER-compute@developer.gserviceaccount.com \
--member=serviceAccount:$PROJECT_NUMBER@cloudbuild.gserviceaccount.com \
--role roles/iam.serviceAccountUser --project=$PROJECT_ID
2. Executar o processo de build
Agora que você informou ao Cloud Build as etapas de build desejadas, está tudo pronto para uma implantação com um clique.
Execute este comando:
gcloud builds submit
Quando o processo terminar, a imagem do contêiner será criada, armazenada no Artifact Registry e implantada no Cloud Run.
Ao final deste codelab, seu app vai ficar igual ao do java17-and-cloud-run/finish.
Pronto! Você migrou um app do App Engine em Java 8 para o Java 17 e o Cloud Run, e agora tem uma compreensão mais clara do trabalho envolvido ao mudar e escolher entre opções de hospedagem.
6. Resumo/limpeza
Parabéns! Você fez upgrade, criou um contêiner e migrou seu app, o que conclui este tutorial.
A próxima etapa é saber mais sobre os recursos de CI/CD e segurança da cadeia de suprimentos de software que estão ao seu alcance agora que você pode fazer implantações com o Cloud Build:
- Como criar etapas de build personalizadas com o Cloud Build
- Criar e gerenciar gatilhos de build
- Como usar a verificação sob demanda no pipeline do Cloud Build
Opcional: limpar e/ou desativar o serviço
Se você implantou o app de exemplo no App Engine durante este tutorial, desative o app para evitar cobranças. Quando estiver pronto para passar para o próximo codelab, você poderá reativá-lo. Enquanto os apps do App Engine estão desativados, eles não recebem tráfego, mas o uso do Datastore pode ser cobrado se exceder a cota sem custo financeiro. Exclua o suficiente para ficar abaixo desse limite.
Por outro lado, se você não quiser continuar com as migrações e quiser excluir tudo completamente, poderá excluir o serviço ou encerrar o projeto completamente.
7. Outros recursos
Problemas/comentários do módulo de migração do App Engine
Se você encontrar problemas com este codelab, pesquise seu problema antes de preenchê-lo. Links para pesquisar e criar novos problemas:
Recursos de migração
- Opções de migração para desagrupar serviços do App Engine
- Como configurar acionadores de build para o Cloud Build
- Mais informações sobre como migrar para o Java 11/17
Recursos on-line
Confira abaixo recursos on-line que podem ser relevantes para este tutorial:
App Engine
- Documentação do App Engine
- Informações sobre preços e cotas do App Engine
- Comparação entre plataformas de primeira e segunda geração
- Suporte de longo prazo para ambientes de execução legados
Outras informações da nuvem
- Nível "Sempre sem custo financeiro" do Google Cloud
- CLI do Google Cloud (CLI
gcloud) - Toda a documentação do Google Cloud
Vídeos
- Serverless Migration Station (em inglês)
- Expedições sem servidor
- Inscreva-se no Google Cloud Tech
- Inscreva-se no Google Developers
Licença
Este conteúdo está sob a licença Atribuição 2.0 Genérica da Creative Commons.