1. סקירה כללית
סדרת הקודלאבס הזו (מדריכים מעשיים וברמת התקדמות עצמית) נועדה לעזור למפתחי Java ב-Google App Engine (Standard) לחדש את האפליקציות שלהם באמצעות הדרכה על סדרת העברות. בעזרת השלבים הבאים תוכלו לעדכן את האפליקציה שלכם כך שתהיה יותר ניידת, ולהחליט אם ליצור אותם בקונטיינרים בשביל Cloud Run, השירות האחיות של Google Cloud לאירוח קונטיינרים עבור App Engine ושירותים אחרים לאירוח קונטיינרים.
במדריך הזה תלמדו איך לארוז אפליקציה של App Engine בקונטיינר כדי לפרוס אותה בשירות המנוהל במלואו של Cloud Run באמצעות Jib. באמצעות Jib אפשר ליצור קובצי אימג' של Docker, פלטפורמה ידועה בתחום לפיתוח, למשלוח ולריצה של אפליקציות בקונטיינרים.
בנוסף להסבר על השלבים הנדרשים כדי לעבור מ-App Engine ל-Cloud Run, תלמדו גם איך לשדרג אפליקציית Java 8 ב-App Engine ל-Java 17.
אם באפליקציה שלכם נעשה שימוש נרחב בשירותים משולבים מדור קודם של App Engine או בתכונות אחרות של App Engine, מומלץ להעביר את השירותים המשולבים האלה או להחליף את התכונות האלה לפני המעבר ל-Cloud Run. אם אתם צריכים עוד זמן כדי לבדוק את אפשרויות ההעברה או אם אתם רוצים להמשיך להשתמש בשירותים המוגדרים מראש מהדור הקודם בינתיים, תוכלו להמשיך לגשת לשירותים המוגדרים מראש של App Engine עבור Java 11/17 כשתשדרגו לסביבת זמן ריצה חדשה יותר. כשהאפליקציה תהיה ניידת יותר, כדאי לחזור אל Codelab הזה כדי ללמוד איך להחיל את ההוראות באפליקציה.
כאן אפשר להבין איך
- שימוש ב-Cloud Shell
- הפעלת ממשקי ה-API של Cloud Run, Artifact Registry ו-Cloud Build
- הכנסת האפליקציה לקונטיינר באמצעות Jib ו-Cloud Build
- פריסת קובצי אימג' של קונטיינרים ב-Cloud Run
מה צריך להכין
- פרויקט ב-Google Cloud Platform עם חשבון פעיל לחיוב ב-GCP והפעלת App Engine
- ידע בעבודה עם פקודות Linux נפוצות
- ידע בסיסי בפיתוח ובפריסה של אפליקציות App Engine
- אפליקציית Servlet של Java 8 שרוצים להעביר ל-Java 17 ולפרוס ב-Cloud Run (זו יכולה להיות אפליקציה ב-App Engine או רק המקור)
סקר
איך תוכלו להשתמש במדריך הזה?
מה מידת שביעות הרצון שלך מהשימוש ב-Java?
איזה דירוג מגיע לדעתך לחוויית השימוש שלך בשירותי Google Cloud?
2. רקע
מערכות פלטפורמה כשירות (PaaS) כמו App Engine ו-Cloud Functions מספקות הרבה יתרונות לצוות ולאפליקציה, למשל, מאפשרות למנהלי מערכות ול-DevOps להתמקד בפיתוח פתרונות. בפלטפורמות ללא שרתים, אפשר להגדיל את האפליקציה באופן אוטומטי לפי הצורך, לצמצם אותה לאפס באמצעות חיוב לפי שימוש כדי לשלוט בעלויות ולהשתמש במגוון שפות פיתוח נפוצות.
עם זאת, הגמישות של קונטיינרים מעניינת גם היא. בזכות היכולת לבחור בכל שפה, בכל ספרייה ובכל תוכנה בינארית, הקונטיינרים מאפשרים לכם ליהנות משני העולמות: הנוחות של עבודה ללא שרת (serverless) יחד עם הגמישות של קונטיינרים. זה המטרה של Cloud Run.
הדרכה על השימוש ב-Cloud Run לא נכללת בקודלאב הזה. מידע נוסף זמין במסמכי התיעוד של Cloud Run. המטרה של המדריך הזה היא להכיר לכם את האופן שבו מעבירים לאריזות קונטיינר אפליקציות של App Engine ל-Cloud Run (או שירותים אחרים שמתארחים בקונטיינרים). לפני שממשיכים, חשוב לדעת כמה דברים, בעיקר שהחוויה של המשתמשים תהיה שונה במקצת.
ב-Codelab הזה תלמדו איך לפתח ולפרוס קונטיינרים. תלמדו איך:
- יצירת קונטיינרים לאפליקציה באמצעות Jib
- מעבר מהגדרת 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:
- התקנה של ה-CLI של
gcloud
או היכרות מחודשת איתו - אתחול ה-CLI של gcloud לפרויקט באמצעות
gcloud init
- יצירת פרויקט App Engine עם
gcloud app create
- פריסת האפליקציה לדוגמה ב-App Engine
./mvnw package appengine:deploy -Dapp.projectId=$PROJECT_ID
- מוודאים שהאפליקציה פועלת ב-App Engine ללא בעיות
4. יצירת מאגר ב-Artifact Registry
אחרי שמעבירים את האפליקציה לקונטיינרים, צריך מקום שבו אפשר לדחוף ולשמור את קובצי האימג'. הדרך המומלצת לעשות זאת ב-Google Cloud היא באמצעות Artifact Registry.
יוצרים את המאגר בשם 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, מומלץ להמשיך לגשת לשירותים האלה ולשדרג לסביבת זמן הריצה החדשה. ה-Codelab הזה מדגים נתיב העברה לאפליקציות שכבר משתמשות בשירותים עצמאיים, או שסביר להניח שאפשר להגדיר אותן מחדש כדי לעשות זאת.
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 כדי לצמצם את ההבדלים בהתנהגות ברירת המחדל אחרי ההעברה. אנחנו יכולים גם להגדיר את גרסת Jetty כך שתתאים לגרסה ש-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. הגדרת 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. אריזה של האפליקציה כקובץ JAR
אפשר לארוז את האפליקציה בקונטיינר באמצעות Jib מ-war, אבל קל יותר לארוז אותה כקובץ JAR שניתן להפעלה. לא נדרשות הרבה הגדרות, במיוחד בפרויקטים שמשתמשים ב-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 ו-Task Queue – שצריך ליצור מחדש באופן ידני. תכונות אלה ידונו בפירוט רב יותר במודולים הבאים.
האפליקציה לדוגמה לא משתמשת בשירותים משולבים מדור קודם, אבל משתמשים שהאפליקציות שלהם משתמשות בשירותים כאלה יכולים לעיין במדריכים הבאים:
- מעבר משירותים הכלולים בחבילה כדי למצוא שירותים עצמאיים מתאימים.
- העברת קובצי תצורה של XML ל-YAML, למשתמשים שעוברים לסביבת זמן ריצה של Java 11/17 בלי להישאר ב-App Engine.
מעכשיו, הפריסה של 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 מאחורי הקלעים כדי לספק חוויית פריסה ללא מאמץ. נעסוק בהרחבה בפריסות מקוד מקור במודולים הבאים.
לחלופין, אם אתם רוצים לשלוט יותר באופן הפריסה של האפליקציה, תוכלו להגדיר קובץ cloudbuild.yaml
שמפרט בבירור את שלבי ה-build שאתם רוצים לבצע:
1. הגדרת קובץ cloudbuild.yaml
יוצרים את קובץ ה-cloudbuild.yaml
הבא באותה רמה כמו הקובץ 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']
אחרי שנודיע ל-Cloud Build לבצע את השלבים הבאים, הוא:
- הרצת הבדיקות באמצעות
./mvnw test
- איך יוצרים, מעבירים בדחיפה ומתייגים את קובץ האימג' ב-Artifact Registry באמצעות Jib
- פריסת האימג' ב-Cloud Run באמצעות
gcloud run deploy
שימו לב שהערך ‘visitors'
מסופק ל-Cloud Run בתור שם השירות הרצוי. הדגל –allow-unauthenticated
מאפשר למשתמשים להיכנס לאפליקציית האינטרנט ללא צורך באימות. חשוב להחליף את PROJECT_ID במזהה הפרויקט שלכם בקובץ cloudbuild.yaml
.
בשלב הבא, מוסיפים את קישורי מדיניות ה-IAM הבאים כדי לאפשר לחשבון השירות של Cloud Build ל-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. הרצת תהליך ה-build
עכשיו, אחרי שסיפקתם ל-Cloud Build את שלבי ה-build הרצויים, אתם מוכנים לפריסה בקליק אחד.
מריצים את הפקודה הבאה:
gcloud builds submit
בסיום התהליך, קובץ האימג' בקונטיינר נוצר, מאוחסן ב-Artifact Registry ופורס ב-Cloud Run.
בסיום הקודלאב, האפליקציה שלכם אמורה להיראות כמו זו שב-java17-and-cloud-run/finish.
זהו, אתה מוכן! העברתם בהצלחה אפליקציית Java 8 App Engine ל-Java 17 ול-Cloud Run, ועכשיו אתם מבינים טוב יותר את העבודה הכרוכה במעבר ובחירה בין אפשרויות האירוח.
6. סיכום/ניקוי
מזל טוב, שדרגתם, העברתם לקונטיינרים והעברתם את האפליקציה. זהו סוף המדריך.
השלב הבא הוא לקבל מידע נוסף על תכונות האבטחה של CI/CD ושרשרת האספקה של תוכנות שנמצאות בהישג יד, שאפשר לפרוס באמצעות Cloud Build:
- יצירת שלבים בהתאמה אישית ל-build באמצעות Cloud Build
- יצירה וניהול של טריגרים לפיתוח גרסאות build
- שימוש בסריקה על פי דרישה בצינור עיבוד הנתונים של Cloud Build
אופציונלי: ניקוי או השבתה של השירות
אם פרסתם את האפליקציה לדוגמה ב-App Engine במהלך המדריך הזה, חשוב לזכור להשבית את האפליקציה כדי להימנע מחיובים. כשתהיו מוכנים לעבור לסדנת הקוד הבאה, תוכלו להפעיל אותו מחדש. למרות שהאפליקציות של App Engine מושבתות, תנועת הגולשים לא תצברו חיובים. עם זאת, ייתכן שאפשר יהיה לחייב את השימוש ב-Datastore אם הוא יחרוג מהמכסה החינמית שלו, לכן צריך למחוק מספיק נתונים כדי לא לחרוג מהמגבלה הזו.
מצד שני, אם אתם לא מתכוונים להמשיך בהעברות ואתם רוצים למחוק הכול לגמרי, תוכלו למחוק את השירות או להשבית את הפרויקט לחלוטין.
7. מקורות מידע נוספים
בעיות/משוב על Codelabs עם מודול ההעברה של App Engine
אם נתקלתם בבעיות בקודלאב הזה, כדאי לחפש את הבעיה לפני ששולחים דיווח. קישורים לחיפוש וליצירה של בעיות חדשות:
מקורות מידע בנושא העברה
- אפשרויות העברה לביטול קיבוץ של שירותי מנוע חיפוש של אפליקציות
- הגדרת טריגרים ל-build ב-Cloud Build
- מידע נוסף על מעבר ל-Java 11/17
משאבים באינטרנט
בהמשך מופיעים מקורות מידע באינטרנט שעשויים להיות רלוונטיים למדריך הזה:
App Engine
- מסמכי העזרה של App Engine
- מידע על תמחור ומכסות של App Engine
- השוואה בין פלטפורמות מדור ראשון לבין פלטפורמות מדור שני
- תמיכה לטווח ארוך בסביבות זמן ריצה מדור קודם
מידע נוסף על Cloud
סרטונים
- תחנת העברה ללא שרת (serverless)
- Serverless Expeditions
- הרשמה ל-Google Cloud Tech
- הרשמה ל-Google Developers
רישיון
העבודה הזו בשימוש במסגרת רישיון Creative Commons Attribution 2.0 Generic.