העברה לקונטיינרים של OCI

בדף הזה מתוארת תשתית הבנייה שנדרשת כדי לשחזר את תהליך build של Cloud Foundry בזמן יצירת תמונות של אפליקציות שתואמות ל-OCI. אם כבר השלמתם את מדריך ההעברה של Spring Music, תוכלו להשתמש במאמר הזה כדי לקבל מידע מעמיק על הגדרות העברה ספציפיות לאפליקציה שלכם.

דיאגרמה שמתארת איך ליצור תמונות OCI באמצעות כלים מודרניים

לפני שמתחילים

  1. מוודאים שהגדרתם פרויקט חדש ל-Cloud Run כמו שמתואר בדף הגדרת Cloud Run.
  2. מוודאים שיש לכם REGISTRY_URI לאחסון קונטיינרים. מומלץ להשתמש ב-Artifact Registry ב-Cloud Run. ‫Docker משמש ליצירת קובצי אימג' ביניים כדי ליצור את הפרויקט.

הגדרת תהליך build שתואם ל-Cloud Foundry

כדי לתמוך בתהליך החדש הזה, צריך ליצור שני קונטיינרים בסיסיים של OCI:

  • קובץ אימג' של builder שמשקף את תהליך ה-build של Cloud Foundry ויכול ליצור קוד מקור של אפליקציה ב-droplets של Cloud Foundry.
  • אימג' של זמן ריצה שמשקף את זמן הריצה של האפליקציה ב-Cloud Foundry.

מנהלי הפלטפורמה צריכים לבצע את התהליך הזה לפחות פעם אחת. אחרי שהתהליך מוגדר, אפשר לשתף את קובצי האימג' של ה-build וההרצה עם כל האפליקציות של Cloud Foundry שצריך להעביר ל-Cloud Run.

יצירת קובץ האימג' של ה-builder

בקטע הזה נוצר קובץ אימג' של build באמצעות cflinux3 כקובץ האימג' הבסיסי. קובץ האימג' ל-build משמש כסביבת ה-build ליצירת קובץ האימג' של האפליקציה.

  1. יוצרים ספרייה בשם build/ ומעבירים אליה את cd:

    mkdir build && cd build
    
  2. בתיקייה build/, יוצרים קובץ חדש בשם Dockerfile ומדביקים בו את הקוד הבא:

    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
    
  3. שימוש ב-Cloud Build כדי ליצור ולפרסם את קובץ האימג' builder

    gcloud builds \
        submit --tag "REGISTRY_URI/builder:stable"
    

    מחליפים את REGISTRY_URI בכתובת של Artifact Registry שבה רוצים לפרסם את אימג' הבנייה. לדוגמה: REGION-docker.pkg.dev/PROJECT_ID/REPOSITORY/builder:stable.

יצירת תמונת זמן הריצה

בקטע הזה נוצרת תמונה של ריצה באמצעות cflinux3 כתמונת הבסיס. תמונת ההרצה משמשת כתמונת הבסיס כשיוצרים את תמונת האפליקציה הסופית.

  1. יוצרים ספרייה בשם run/ ומעבירים אליה את cd:

    mkdir run && cd run
    
  2. בתיקייה run/, יוצרים סקריפט מעטפת חדש בשם entrypoint.bash עם הקוד הבא:

    #!/usr/bin/env bash
    set -e
    
    if [[ "$@" == "" ]]; then
    exec /lifecycle/launcher "/home/vcap/app" "" ""
    else
    exec /lifecycle/launcher "/home/vcap/app" "$@" ""
    fi
    
  3. בתיקייה run/, יוצרים קובץ חדש בשם Dockerfile ומדביקים בו את הקוד הבא:

    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={}
    
  4. משתמשים ב-Cloud Build כדי ליצור ולפרסם את קובץ האימג' runtime:

    gcloud builds submit \
        --tag "REGISTRY_URI/runtime:stable"
    

    מחליפים את REGISTRY_URI בכתובת של Artifact Registry שבה רוצים לפרסם את אימג' ה-build. לדוגמה: REGION-docker.pkg.dev/PROJECT_ID/REPOSITORY/runtime:stable.

יצירת אפליקציות Cloud Foundry כקובצי אימג' של OCI

לכל אפליקציה שמועברת ל-Cloud Run צריך להיות קובץ Dockerfile משלה, שתואם לאופן שבו Cloud Foundry מריץ אפליקציות. קובץ ה-Dockerfile מבצע את הפעולות הבאות:

  • טעינת קובץ האימג' של ה-builder.
  • מריצים את מחזור החיים של חבילת ה-buildpack בגרסה 2 כדי ליצור droplet.
  • מחולץ התוכן של הטיפה.
  • טוען את התוכן של ה-droplet בתמונת ההרצה כדי ליצור את תמונת האפליקציה שניתנת להרצה.

קובץ האימג' הסופי של האפליקציה תואם ל-Cloud Foundry ול-Cloud Run, כך שתוכלו לבצע בדיקת A/B של ההעברה כדי לנפות באגים בהתנהגות לא צפויה.

צוות האפליקציה צריך לבצע את התהליך הזה לכל אפליקציה שצריך להעביר.

איסוף מידע על בנייה מאפליקציית Cloud Foundry שפריסתה הושלמה

  1. בודקים את ערימת האפליקציות. המידע על ה-stack מסופק באמצעות הדגל -s ב-cf push או בשדה stack של מניפסט האפליקציה.

    1. אם הסטאק הוא Windows, סביר להניח שהאפליקציה לא תואמת ל-Cloud Run. כדי להמשיך, צריך להעביר את האפליקציה ל-Linux.
    2. אם מחסנית הטכנולוגיות ריקה, cflinuxfs3 או cflinuxfs4, אפשר להעביר את האפליקציה ל-Cloud Run.
  2. מכינים את רשימת ה-buildpacks של האפליקציה. חבילות Buildpack מסופקות באמצעות הדגל -b ב-cf push, השדה buildpack במניפסט האפליקציה או השדה buildpacks במניפסט האפליקציה.

    1. אם לא מציינים buildpacks, המשמעות היא שהם מזוהים אוטומטית. מעיינים ברשימת חבילות ה-buildpack שזוהו בפריסת האפליקציה האחרונה ב-Cloud Foundry, או מציינים אותן באופן מפורש אם אתם יודעים את הנתיבים.
    2. אם חבילות ה-buildpack הן כתובות URL, רושמים את כתובות ה-URL וממשיכים לשלב הבא.
    3. אם משתמשים ב-buildpack עם שם מקוצר, אפשר להשתמש בטבלה הבאה כדי למפות אותו לכתובת URL:

      שם מקוצר כתובת URL
      staticfile_buildpack https://github.com/cloudfoundry/staticfile-buildpack
      java_buildpack https://github.com/cloudfoundry/java-buildpack
      ruby_buildpack https://github.com/cloudfoundry/ruby-buildpack
      dotnet_core_buildpack https://github.com/cloudfoundry/dotnet-core-buildpack
      nodejs_buildpack https://github.com/cloudfoundry/nodejs-buildpack
      go_buildpack https://github.com/cloudfoundry/go-buildpack
      python_buildpack https://github.com/cloudfoundry/python-buildpack
      php_buildpack https://github.com/cloudfoundry/php-buildpack
      binary_buildpack https://github.com/cloudfoundry/binary-buildpack
      nginx_buildpack https://github.com/cloudfoundry/nginx-buildpack

      אפשר למצוא את המקור של חבילות buildpack פחות נפוצות בארגון Cloud Foundry GitHub.

  3. מאתרים את קוד המקור של התמונה. המקור מסופק באמצעות המאפיין path של מניפסט האפליקציה או הדגל -p של הפקודה cf push. אם המקור לא מוגדר, הוא מתייחס לספרייה הנוכחית.

  4. בודקים אם יש קובץ .cfignore בספריית קוד המקור. אם הוא נמצא שם, מעבירים אותו לקובץ בשם .gcloudignore.

פיתוח אפליקציית Cloud Foundry

בשלב הזה, מארגנים את רכיבי ה-build במבנה התיקיות הבא:

.
├── cloudbuild.yaml
├── Dockerfile
├── .gcloudignore
└── src
    ├── go.mod
    └── main.go
  • cloudbuild.yaml מספק ל-Cloud Build הוראות בנייה ספציפיות
  • Dockerfile ישתמש בתמונות של build ו-run מהשלבים הקודמים כדי ליצור את תמונת האפליקציה
  • src/ מכיל את קוד המקור של האפליקציה
  1. יוצרים קובץ בשם 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
    
  2. יוצרים קובץ בשם 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: BUILD_IMAGE_URI
      _RUN_IMAGE:  RUN_IMAGE_URI
      _BUILDPACKS: BUILDPACK_URL
      _TAG: APP_ARTIFACT_REGISTRY/APP_NAME:latest
    
    • מחליפים את BUILD_IMAGE_URI ב-URI של קובץ האימג' של ה-build שנוצר בשלבים הקודמים.
    • מחליפים את RUN_IMAGE_URI ב-URI של תמונת ההפעלה שנוצרה בשלבים הקודמים.
    • מחליפים את BUILDPACK_URL בכתובות ה-URL של חבילות ה-buildpack שבהן נעשה שימוש באפליקציה. אפשר להזין רשימה מופרדת בפסיקים עם כמה חבילות buildpack.
  3. אם יש לכם קובץ .cfignore, מעתיקים אותו לספרייה עם השם .gcloudignore.

  4. יוצרים ספרייה בשם src בספרייה.

  5. מעתיקים את התוכן של הבקשה אל src:

    1. אם המקור הוא קובץ ZIP (כולל קובצי .jar), צריך לבטל את הדחיסה של התוכן לתוך src.
    2. אם קוד המקור הוא ספרייה, מעתיקים את התוכן אל src.
  6. מריצים את הפקודה gcloud builds submit . כדי ליצור את האפליקציה.

בעיות תאימות ידועות

  • ‫Buildpacks שמסתמכים על משתני סביבה שמוזרקים על ידי Cloud Foundry, כמו VCAP_SERVICES, לא יפעלו. במקום זאת, צריך להצהיר במפורש על תלות במה שהם מזריקים באמצעות מערכת הניהול של השפה.
  • כדי לתקן את התמונות שנוצרו בדרך הזו, צריך לבנות מחדש את התמונה באמצעות גרסה חדשה יותר של תמונת הבנייה וההפעלה. אם מריצים תמונות של אפליקציות ב-Cloud Foundry, הן לא יתוקנו אוטומטית על ידי עדכון של BOSH stemcells.
  • הגרסאות ייווצרו בסביבת רשת שונה מזו של אשכול Cloud Foundry, ולכן יכול להיות שתצטרכו להגדיר מאגרי Cloud Build בהתאמה אישית עם גישה למאגרי החבילות הפנימיים שלכם.

המאמרים הבאים