En esta migración de ejemplo se usa el proyecto Spring Music para mostrar cómo se puede compilar una aplicación de Cloud Foundry como una imagen de aplicación compatible con OCI. En este ejemplo se usa la estrategia de migración lift and shift, que utiliza componentes de código abierto del ecosistema de Cloud Foundry. Una vez que hayas creado la imagen de la aplicación, tendrás que configurarla para desplegarla en Cloud Run.
Antes de empezar
- Asegúrate de haber configurado un proyecto para Cloud Run tal como se describe en la página de configuración.
- Asegúrate de tener un
REGISTRY_URI
para almacenar contenedores. Cloud Run recomienda usar Artifact Registry. Si tu proyecto está sujeto a una política de organización de restricción de dominio que restringe las invocaciones no autenticadas, tendrás que acceder al servicio desplegado tal como se describe en la sección Probar servicios privados.
- Instala Docker en tu estación de trabajo. Docker se usa para crear imágenes intermedias con las que compilar el proyecto.
Permisos necesarios para implementar
Para seguir esta guía, necesitas permisos para compilar, almacenar la imagen de contenedor compilada y desplegarla.
Debes tener los siguientes roles:
- Rol Editor de Cloud Build
- Rol Administrador de Artifact Registry
- Rol Administrador de almacenamiento
- Rol Administrador de Cloud Run
- Rol Usuario de cuenta de servicio
Estructura del proyecto
En esta guía, te recomendamos que crees un directorio de proyecto, por ejemplo, cr-spring-music/
y que crees subdirectorios a medida que avances en la guía.
cr-spring-music/
├── build
├── run
└── spring-music
Crea la imagen de compilación
En esta sección se crea una imagen de compilación usando cflinux3
como imagen base. La imagen de compilación se usa como entorno de compilación para crear la imagen de la aplicación.
Crea un directorio llamado
build/
ycd
en él:mkdir build && cd build
En la carpeta
build/
, crea un archivo llamadoDockerfile
y pega el siguiente código:ARG CF_LINUX_FS=cloudfoundry/cflinuxfs3 FROM golang:1.20-bullseye AS builder_build WORKDIR /build RUN ["git", "clone", "--depth=1", "https://github.com/cloudfoundry/buildpackapplifecycle.git"] WORKDIR /build/buildpackapplifecycle RUN ["go", "mod", "init", "code.cloudfoundry.org/buildpackapplifecycle"] RUN ["go", "mod", "tidy"] RUN CGO_ENABLD=0 go build -o /builder ./builder/ FROM $CF_LINUX_FS # Set up container tools related to building applications WORKDIR /lifecycle COPY --from=builder_build /builder /lifecycle/builder # Set up environment to match Cloud Foundry's build. # https://docs.cloudfoundry.org/devguide/deploy-apps/environment-variable.html#app-system-env WORKDIR /staging/app WORKDIR /tmp ENV CF_INSTANCE_ADDR=127.0.0.1:8080 \ CF_INSTANCE_IP=127.0.0.1 \ CF_INSTANCE_INTERNAL_IP=127.0.0.1 \ VCAP_APP_HOST=127.0.0.1 \ CF_INSTANCE_PORT=8080 \ LANG=en_US.UTF-8 \ INSTANCE_GUID=00000000-0000-0000-0000-000000000000 \ VCAP_APPLICATION={} \ VCAP_SERVICES={} \ CF_STACK=cflinuxfs3
Usar Cloud Build para compilar y publicar la imagen
builder
gcloud builds \ submit --tag "REGISTRY_URI/builder:stable"
Sustituye
REGISTRY_URI
por la dirección de Artifact Registry en la que quieras publicar la imagen de compilación. Por ejemplo:REGION-docker.pkg.dev/PROJECT_ID/REPOSITORY/builder:stable
.
Crear la imagen de tiempo de ejecución
En esta sección se crea una imagen de ejecución usando cflinux3
como imagen base. La imagen de ejecución se usa como imagen base al crear la imagen de aplicación final.
Crea un directorio llamado
run/
ycd
en él:mkdir run && cd run
En la carpeta
run/
, crea una secuencia de comandos shell llamadaentrypoint.bash
con el siguiente código:#!/usr/bin/env bash set -e if [[ "$@" == "" ]]; then exec /lifecycle/launcher "/home/vcap/app" "" "" else exec /lifecycle/launcher "/home/vcap/app" "$@" "" fi
En la carpeta
run/
, crea un archivo llamadoDockerfile
y pega el siguiente código:ARG CF_LINUX_FS=cloudfoundry/cflinuxfs3 FROM golang:1.20-bullseye AS launcher_build WORKDIR /build RUN ["git", "clone", "--depth=1", "https://github.com/cloudfoundry/buildpackapplifecycle.git"] WORKDIR /build/buildpackapplifecycle RUN ["go", "mod", "init", "code.cloudfoundry.org/buildpackapplifecycle"] RUN ["go", "mod", "tidy"] RUN CGO_ENABLD=0 go build -o /launcher ./launcher/ FROM $CF_LINUX_FS # Set up container tools related to launching the application WORKDIR /lifecycle COPY entrypoint.bash /lifecycle/entrypoint.bash RUN ["chmod", "+rx", "/lifecycle/entrypoint.bash"] COPY --from=launcher_build /launcher /lifecycle/launcher # Set up environment to match Cloud Foundry WORKDIR /home/vcap USER vcap:vcap ENTRYPOINT ["/lifecycle/entrypoint.bash"] # Expose 8080 to allow app to be run on Cloud Foundry, # and PORT so the container can be run locally. # These do nothing on Cloud Run. EXPOSE 8080/tcp # Set up environment variables similar to Cloud Foundry. ENV CF_INSTANCE_ADDR=127.0.0.1:8080 \ CF_INSTANCE_IP=127.0.0.1 \ INSTANCE_IP=127.0.0.1 \ CF_INSTANCE_INTERNAL_IP=127.0.0.1 \ VCAP_APP_HOST=127.0.0.1 \ CF_INSTANCE_PORT=80 \ LANG=en_US.UTF-8 \ CF_INSTANCE_GUID=00000000-0000-0000-0000-000000000000 \ INSTANCE_GUID=00000000-0000-0000-0000-000000000000 \ CF_INSTANCE_INDEX=0 \ INSTANCE_INDEX=0 \ PORT=8080 \ VCAP_APP_PORT=8080 \ VCAP_APPLICATION={} \ VCAP_SERVICES={}
Usa Cloud Build para compilar y publicar la imagen
runtime
:gcloud builds submit \ --tag "REGISTRY_URI/runtime:stable"
Sustituye
REGISTRY_URI
por la dirección de Artifact Registry en la que quieras publicar la imagen de compilación. Por ejemplo:REGION-docker.pkg.dev/PROJECT_ID/REPOSITORY/runtime:stable.
Compilar Spring Music para Cloud Foundry
Para clonar el proyecto Spring Music y ejecutar los comandos de compilación como si fuéramos a desplegar el proyecto en Cloud Foundry, haz lo siguiente:
Clona el repositorio Spring Music:
git clone https://github.com/cloudfoundry-samples/spring-music.git
En esta guía, usaremos una versión anterior de la aplicación Spring Music que utiliza Java 8 y Spring Boot 2. Para ello, vamos a cambiar a una revisión anterior del proyecto Spring Music:
git checkout 610ba471a643a20dee7a62d88a7879f13a21d6a3
Ve al repositorio:
cd spring-music
Compila el archivo binario de Spring Music:
./gradlew clean assemble
Ahora tienes una carpeta build/
con la aplicación Spring Music compilada, lista para insertarse en una instancia de Cloud Foundry.
Convertir Spring Music en una aplicación compatible con Cloud Run
Debes usar el resultado del comando de compilación para preparar el artefacto de Spring Music para su despliegue en Cloud Run.
Crea un directorio de ensayo
cr-app
y un subdirectoriosrc
dentro de él:mkdir -p cr-app/src
Imita
cf push
extrayendo el contenido del archivo JAR compilado en el directoriosrc
:unzip build/libs/spring-music-1.0.jar -d cr-app/src
Cambia al directorio
cr-app/
:cd cr-app/
Crea un archivo llamado
Dockerfile
. EsteDockerfile
usará la imagen de compilación y la imagen de tiempo de ejecución creadas en los pasos anteriores para crear la imagen de la aplicación ejecutable de Spring Music, mediante el paquete de compilación de Java.Pegue el siguiente código en el archivo
Dockerfile
:ARG BUILD_IMAGE ARG RUN_IMAGE FROM $BUILD_IMAGE as build COPY src /staging/app COPY src /tmp/app ARG BUILDPACKS RUN /lifecycle/builder \ -buildArtifactsCacheDir=/tmp/cache \ -buildDir=/tmp/app \ -buildpacksDir=/tmp/buildpacks \ -outputBuildArtifactsCache=/tmp/output-cache \ -outputDroplet=/tmp/droplet \ -outputMetadata=/tmp/result.json \ "-buildpackOrder=${BUILDPACKS}" \ "-skipDetect=true" FROM $RUN_IMAGE COPY --from=build /tmp/droplet droplet RUN tar -xzf droplet && rm droplet
Compilar Spring Music como una imagen compatible con OCI
En este paso, le indicas a Cloud Build cómo crear una imagen compatible con OCI mediante la imagen de compilación, la imagen de tiempo de ejecución y el Dockerfile de la aplicación que has creado en los pasos anteriores.
Para crear la imagen compatible con OCI, sigue estos pasos:
Crea un archivo llamado
cloudbuild.yaml
. Esta es una configuración de compilación que indicará a Cloud Build cómo compilar la aplicación.Pega la siguiente configuración en
cloudbuild.yaml
:steps: - name: gcr.io/cloud-builders/docker args: - 'build' - '--network' - 'cloudbuild' - '--tag' - '${_TAG}' - '--build-arg' - 'BUILD_IMAGE=${_BUILD_IMAGE}' - '--build-arg' - 'RUN_IMAGE=${_RUN_IMAGE}' - '--build-arg' - 'BUILDPACKS=${_BUILDPACKS}' - '.' images: - "${_TAG}" options: # Substitute build environment variables as an array of KEY=VALUE formatted strings here. env: [] substitutions: _BUILD_IMAGE: REGISTRY_URI/builder:stable _RUN_IMAGE: REGISTRY_URI/runtime:stable _BUILDPACKS: https://github.com/cloudfoundry/java-buildpack _TAG: REGISTRY_URI/spring-music:latest
- Sustituye
REGISTRY_URI
por el URI del registro de contenedores en el que has publicado el compilador y el ejecutor.
- Sustituye
Crea la imagen de la aplicación con Cloud Build:
gcloud builds submit .
Cuando se complete la compilación, anota el URI de la imagen resultante. Lo necesitarás para implementar la aplicación en los pasos siguientes. La imagen resultante será una imagen de contenedor compatible con OCI para ejecutar la aplicación Spring Music, creada con componentes de código abierto de Cloud Foundry.
Desplegar en Cloud Run
Debes crear un archivo de definición de servicio para usarlo en Cloud Run:
Crea una cuenta de servicio para tu aplicación:
gcloud iam service-accounts create spring-music
Crea un archivo
service.yaml
con el siguiente código:apiVersion: serving.knative.dev/v1 kind: Service metadata: name: "spring-music" # Set this to be the project number of the project you're deploying to. namespace: "PROJECT_NUMBER" labels: cloud.googleapis.com/location: us-central1 migrated-from: cloud-foundry annotations: run.googleapis.com/ingress: all spec: template: metadata: annotations: autoscaling.knative.dev/minScale: '1' autoscaling.knative.dev/maxScale: '1' run.googleapis.com/cpu-throttling: 'true' run.googleapis.com/startup-cpu-boost: 'true' run.googleapis.com/sessionAffinity: 'false' spec: containerConcurrency: 1000 timeoutSeconds: 900 serviceAccountName: spring-music@PROJECT_NUMBER.iam.gserviceaccount.com containers: - name: user-container # Set the following value to either: # - The image you built for your application in the last section of the guide. image: SPRING_IMAGE_URI ports: - name: http1 containerPort: 8080 env: - name: VCAP_APPLICATION value: |- { "application_id": "00000000-0000-0000-0000-000000000000", "application_name": "spring-music", "application_uris": [], "limits": { "disk": 0, "mem": 1024 }, "name": "spring-music", "process_id": "00000000-0000-0000-0000-000000000000", "process_type": "web", "space_name": "none", "uris": [] } - name: MEMORY_LIMIT value: '1024M' resources: limits: memory: 1024Mi cpu: "1" startupProbe: httpGet: path: / port: 8080 timeoutSeconds: 1 failureThreshold: 30 successThreshold: 1 periodSeconds: 2 livenessProbe: httpGet: path: / port: 8080 timeoutSeconds: 1 failureThreshold: 1 successThreshold: 1 periodSeconds: 30 traffic: - percent: 100 latestRevision: true
- Sustituye
PROJECT_NUMBER
por el número de tu proyecto. - Sustituye
SPRING_IMAGE_URI
por el URI de la imagen de la aplicación creada en Crear Spring Music como una imagen compatible con OCI.
- Sustituye
Despliega el servicio en Cloud Run:
gcloud run services replace service.yaml
Una vez que se haya completado la implementación, podrás visitar la aplicación Spring Music en la URL implementada.
Siguientes pasos
- Para obtener información más detallada sobre el proceso de contenerización, consulta Migrar a contenedores OCI.