מעבר מאפליקציית Google App Engine Java ל-Cloud Run באמצעות Buildpacks

1. סקירה כללית

סדרת הקודלאבס הזו (מדריכים מעשיים וברמת התקדמות עצמית) נועדה לעזור למפתחי Java ב-Google App Engine (Standard) לחדש את האפליקציות שלהם באמצעות הדרכה על סדרת העברות. בעזרת השלבים הבאים תוכלו לעדכן את האפליקציה שלכם כך שתהיה יותר ניידת, ולהחליט אם ליצור אותם בקונטיינרים בשביל Cloud Run, השירות האחיות של Google Cloud לאירוח קונטיינרים עבור App Engine ושירותים אחרים לאירוח קונטיינרים.

במדריך הזה תלמדו איך להעביר אפליקציה של App Engine לקונטיינר כדי לפרוס אותה בשירות המנוהל במלואו של Cloud Run באמצעות Buildpacks. ‏Buildpacks הם פרויקט של CNCF שמאפשר לכם להעביר את האפליקציה ישירות מקוד המקור לקובצי אימג' ניידים במיוחד שאפשר להריץ בכל ענן.

בנוסף להסבר על השלבים הנדרשים כדי לעבור מ-App Engine ל-Cloud Run, תלמדו גם איך לשדרג אפליקציית Java 8 ב-App Engine ל-Java 17.

אם האפליקציה שאתם רוצים להעביר משתמשת הרבה בשירותים המוגדרים מראש מדור קודם של App Engine או בתכונות ספציפיות אחרות של App Engine, יכול להיות שהמדריך גישה לשירותים המוגדרים מראש של App Engine עבור Java 11/17 יתאים לכם יותר מאשר הקודלאב הזה.

כאן תלמדו איך

  • שימוש ב-Cloud Shell
  • הפעלת ממשקי ה-API של Cloud Run, Artifact Registry ו-Cloud Build
  • יצירת קונטיינרים לאפליקציה באמצעות Buildpacks ב-Cloud Build
  • פריסת קובצי האימג' של הקונטיינרים ב-Cloud Run

מה צריך להכין

סקר

איך תשתמשו במדריך הזה?

לקריאה בלבד לקריאת התרגילים ולהשלמת התרגילים

מה מידת שביעות הרצון שלך מהשימוש ב-Java?

מתחילים בינוניים מומחים

איזה דירוג מגיע לדעתך לחוויית השימוש שלך בשירותי Google Cloud?

מתחילים בינוניים מומחים

2. רקע

מערכות PaaS כמו App Engine ו-Cloud Functions מספקות לצוות ולאפליקציה שלכם אפשרויות נוחות רבות. למשל, הן מאפשרות ל-SysAdmins ול-Devops להתמקד בפיתוח פתרונות. בפלטפורמות ללא שרתים, אפשר להגדיל את האפליקציה באופן אוטומטי לפי הצורך, לצמצם אותה לאפס באמצעות חיוב לפי שימוש כדי לשלוט בעלויות ולהשתמש במגוון שפות פיתוח נפוצות.

עם זאת, הגמישות של הקונטיינרים היא גם יתרון משמעותי. בזכות היכולת לבחור בכל שפה, בכל ספרייה ובכל תוכנה בינארית, הקונטיינרים מאפשרים לכם ליהנות משני העולמות: הנוחות של עבודה ללא שרת (serverless) יחד עם הגמישות של קונטיינרים. זהו המהות של Google Cloud Run.

שיעור השימוש ב-Cloud Run לא נכלל בקורס הזה של Codelab. יש הסבר במסמכי התיעוד של Cloud Run. המטרה של המדריך הזה היא להכיר לכם את האופן שבו מעבירים לאריזות קונטיינר אפליקציות של App Engine ל-Cloud Run (או שירותים אחרים שמתארחים בקונטיינרים). לפני שממשיכים, חשוב לדעת כמה דברים, בעיקר שהחוויה של המשתמשים תהיה שונה במקצת.

ב-codelab הזה תלמדו איך ליצור ולפרוס קונטיינרים. תלמדו איך להעביר את האפליקציה לקונטיינרים באמצעות Buildpacks, איך לעבור מהגדרות של App Engine ולהגדיר שלבי build ב-Cloud Build. כדי לעשות זאת, תצטרכו להפסיק להשתמש בתכונות מסוימות שספציפיות ל-App Engine. אם אתם מעדיפים לא לפעול לפי הנתיב הזה, עדיין תוכלו לשדרג לסביבת זמן ריצה של Java 11/17 תוך שמירה על האפליקציות ב-App Engine.

3. הגדרה/עבודה מוקדמת

1. הגדרת פרויקט

במדריך הזה נשתמש באפליקציית דוגמה מהמאגר appengine-java-migration-samples בפרויקט חדש לגמרי. מוודאים שלפרויקט יש חשבון פעיל לחיוב.

אם אתם מתכוונים להעביר אפליקציית App Engine קיימת ל-Cloud Run, תוכלו להשתמש באפליקציה הזו במקום זאת.

מריצים את הפקודה הבאה כדי להפעיל את ממשקי ה-API הנדרשים לפרויקט:

gcloud services enable artifactregistry.googleapis.com cloudbuild.googleapis.com run.googleapis.com

2. הורדת אפליקציית דוגמה

משכפלים את האפליקציה לדוגמה במכונה שלכם או ב-Cloud Shell, ועוברים אל התיקייה baseline.

הדוגמה היא אפליקציית Datastore מבוססת-Servlet של Java 8, שמיועדת לפריסה ב-App Engine. פועלים לפי ההוראות במסמך README כדי להכין את האפליקציה לפריסה ב-App Engine.

3. (אופציונלי) פורסים את אפליקציית הבקרה

השלבים הבאים נדרשים רק אם רוצים לוודא שהאפליקציה פועלת ב-App Engine לפני שאנחנו מעבירים אותה ל-Cloud Run.

יש לעיין בשלבים שבקובץ README.md:

  1. התקנה של ה-CLI של gcloud או היכרות מחודשת איתו
  2. אתחול ה-CLI של gcloud לפרויקט עם gcloud init
  3. יצירת הפרויקט ב-App Engine באמצעות gcloud app create
  4. פריסת האפליקציה לדוגמה ב-App Engine
./mvnw package appengine:deploy -Dapp.projectId=$PROJECT_ID
  1. מוודאים שהאפליקציה פועלת ב-App Engine ללא בעיות

4. יצירת מאגר ב-Artifact Registry

לאחר יצירת הקונטיינרים של האפליקציה, יהיה צורך במקום כלשהו כדי לדחוף ולאחסן את התמונות. מומלץ להשתמש ב-Artifact Registry כדי לעשות את זה ב-Google Cloud.

יוצרים את המאגר בשם migration באמצעות gcloud באופן הבא:

gcloud artifacts repositories create migration --repository-format=docker \
--description="Docker repository for the migrated app" \
--location="northamerica-northeast1"

הערה: המאגר הזה משתמש בפורמט docker, אבל יש כמה סוגים של מאגרים זמינים.

בשלב הזה, יש לכם את אפליקציית App Engine הבסיסית, והפרויקט ב-Google Cloud מוכן להעברה ל-Cloud Run.

4. שינוי קובצי אפליקציה

במקרים שבהם האפליקציה שלכם משתמשת באופן נרחב בשירותים המוגדרים מראש, בהגדרות או בתכונות אחרות של App Engine מדור קודם, שזמינות רק ב-App Engine, מומלץ להמשיך לגשת לשירותים האלה בזמן השדרוג לסביבת זמן הריצה החדשה. בקודלאב הזה מוצג מסלול העברה לאפליקציות שכבר משתמשות בשירותים עצמאיים, או שאפשר לבצע בהן רפאקציה כדי לעשות זאת.

1. שדרוג ל-Java 17

אם האפליקציה שלכם מבוססת על Java 8, כדאי לשדרג לגרסה מתקדמת יותר של LTS, כמו 11 או 17, כדי לעמוד בקצב של עדכוני האבטחה ולקבל גישה לתכונות חדשות של השפה.

קודם כול צריך לעדכן את המאפיינים ב-pom.xml כך שיכללו את הרכיבים הבאים:

<properties>
    <java.version>17</java.version>
    <maven.compiler.source>17</maven.compiler.source>
    <maven.compiler.target>17</maven.compiler.target>
</properties>

הפעולה הזו תגדיר את גרסת הפרויקט ל-17, תודיע לפלאגין של המהדר שרוצים גישה לתכונות השפה של Java 17 ושרוצים שהכיתות המתורגמות יהיו תואמות ל-JVM של Java 17.

2. כולל שרת אינטרנט

יש כמה הבדלים בין App Engine לבין Cloud Run שכדאי לקחת בחשבון כשעוברים ביניהם. הבדל אחד הוא שבזמן הריצה של Java 8 ב-App Engine, שרתי Jetty סיפקו וניהול את האפליקציות שהשירות אירח, אבל ב-Cloud Run אין שרתי Jetty. נשתמש ב-Spring Boot כדי לספק לנו שרת אינטרנט ומאגר Servlet.

מוסיפים את יחסי התלות הבאים:

<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>

Spring Boot מטמיע שרת Tomcat כברירת מחדל, אבל הדוגמה הזו תחרוג מהכלל הזה ותשתמש ב-Jetty כדי לצמצם את ההבדלים בהתנהגות ברירת המחדל אחרי ההעברה.

3. הגדרת Spring Boot

Spring Boot יוכל לעשות שימוש חוזר ב-servlets בלי שינוי, אבל תצטרכו לבצע הגדרות מסוימות כדי לוודא שהם ניתנים לגילוי.

יוצרים את המחלקה הבאה MigratedServletApplication.java בחבילה 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);
    }
}

שימו לב שהערה @ServletComponentScan נכללת בכך, והיא תבדוק (בחבילת הקוד הנוכחית כברירת מחדל) אם יש @WebServlets, ותהפוך אותם לזמינים כצפוי.

4. הגדרת build

בשלב הבא מסירים את ההגדרה כדי לארוז את האפליקציה כקובץ WAR. לא נדרשות הרבה הגדרות, במיוחד בפרויקטים שמשתמשים ב-Maven ככלי build – מכיוון שאריזת jar היא ברירת המחדל.

מסירים את התג packaging מהקובץ pom.xml:

<packaging>war</packaging>

לאחר מכן מוסיפים את 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. מעבר מההגדרות, מהשירותים ומהיחסי התלות של App Engine

כפי שצוין בתחילת הקודלאב, Cloud Run ו-App Engine נועדו לספק חוויות משתמש שונות. יש תכונות מסוימות ש-App Engine מציע מחוץ לאריזה, כמו השירותים Cron ותור משימות, שצריך ליצור מחדש באופן ידני, וניתן ללמוד עליהן בפירוט במודולים מאוחרים יותר.

האפליקציה לדוגמה לא משתמשת בשירותים משולבים מדור קודם, אבל משתמשים שהאפליקציות שלהם משתמשות בשירותים כאלה יכולים לעיין במדריכים הבאים:

מעכשיו והלאה תבצעו פריסה ב-Cloud Run, כך שאפשר להסיר את appengine-maven-plugin:

<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. יצירת קונטיינרים ופריסה של אפליקציות

בשלב הזה אתם מוכנים לפרוס את האפליקציה ב-Cloud Run ישירות מקוד המקור. זוהי אפשרות מצוינת שמשתמשת ב-Cloud Build מאחורי הקלעים כדי לספק חוויית פריסה ללא מאמץ. חשוב לדעת: כדי להשתמש בתכונה הזו, צריך חשבון עם לפחות אחת מההרשאות הבאות, ופעולת לפי השלבים להגדרת הסביבה – או להשתמש ב-Cloud Shell:

אחרי שמבצעים את התנאים המוקדמים האלה, פשוט מריצים את הפקודה הבאה מהספרייה המקורית:

gcloud run deploy SERVICE --source .

במהלך הפעלת הפקודה deploy תתבקשו לספק כמה פרטים, כמו:

  • ציון המיקום של קוד המקור
  • ציון שם השירות
  • הפעלת Cloud Run API
  • בחירת האזור שלך

אחרי שמגיבים להנחיות האלה, תהליך ה-build והפריסה מתחיל, ובמהלכו Cloud Build מבצע את הפעולות הבאות:

  • קובץ ה-zip נשמר בקטגוריה של אחסון בענן
  • משתמש ב-buildpacks של Cloud Native Computing Foundation ברקע כדי ליצור את קובץ האימג'
  • יוצרת מאגר לאחסון קובץ האימג' שנוצר בקונטיינר (אם הוא עדיין לא קיים)
  • יצירת שירות של הפעלה בענן לאירוח האפליקציה (אם היא לא קיימת)

לאחר השלמת ה-build והפריסה, אמורה להופיע הודעה המסבירה שגרסה חדשה פעילה ומשרתת 100% מהתנועה.

6. סיכום/ניקוי

מזל טוב, שדרגתם, העברתם לקונטיינרים והעברתם את האפליקציה. זהו סוף המדריך.

השלב הבא הוא לקבל מידע נוסף על תכונות האבטחה של CI/CD ושרשרת האספקה של תוכנות שנמצאות בהישג יד, שאפשר לפרוס באמצעות Cloud Build:

אופציונלי: ניקוי או השבתה של השירות

אם פרסתם את האפליקציה לדוגמה ב-App Engine במהלך המדריך הזה, חשוב לזכור להשבית את האפליקציה כדי להימנע מחיובים. כשתהיו מוכנים לעבור ל-Codelab הבא, תוכלו להפעיל אותו מחדש. כשאפליקציות App Engine מושבתות, הן לא מקבלות תנועה ולכן לא נצברות עליהן חיובים. עם זאת, יכול להיות שתחויבו על שימוש במאגר הנתונים אם תחרגו מהמכסה ללא תשלום, לכן כדאי למחוק מספיק נתונים כדי להישאר במסגרת המגבלה הזו.

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

7. מקורות מידע נוספים

בעיות/משוב על Codelabs עם מודול ההעברה של App Engine

אם נתקלתם בבעיות בקודלאב הזה, כדאי לחפש את הבעיה לפני ששולחים דיווח. קישורים לחיפוש וליצירה של בעיות חדשות:

מקורות מידע בנושא העברה

משאבים באינטרנט

בהמשך מופיעים מקורות מידע באינטרנט שעשויים להיות רלוונטיים למדריך הזה:

App Engine

מידע נוסף על Cloud

סרטונים

רישיון

העבודה הזו בשימוש במסגרת רישיון Creative Commons Attribution 2.0 Generic.