סקירה כללית של פרופילים בסיסיים

פרופילי בסיס משפרים את מהירות ביצוע הקוד בכ-30% מההפעלה הראשונה, על ידי הימנעות מפרשנות ומשלבי הידור בזמן אמת (JIT) עבור נתיבי קוד כלולים.

כשמצרפים פרופיל בסיסי לאפליקציה או לספרייה, Android Runtime (ART) יכול לבצע אופטימיזציה של נתיבי קוד ספציפיים באמצעות קומפילציה מראש (AOT), וכך לשפר את הביצועים לכל משתמש חדש ולכל עדכון של האפליקציה. אופטימיזציה מונחית פרופיל (PGO) מאפשרת לאפליקציות לבצע אופטימיזציה של ההפעלה, לצמצם את הבעיות שקשורות לאינטראקציה ולשפר את הביצועים הכוללים של זמן הריצה למשתמשים מההפעלה הראשונה.

השיפורים האלה בביצועים מובילים ישירות לשיפור המדדים העסקיים, כמו שימור משתמשים, עסקאות ודירוגים. אפשר לקרוא עוד על ההשפעה של הביצועים על מדדים עסקיים בסיפורים של Josh,‏ Lyft,‏ TikTok ו-Zomato.

היתרונות של פרופילי Baseline

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

פרופילים בסיסיים עוזרים לבצע אופטימיזציה מעבר להפעלה של האפליקציה, כי הם מספקים אינטראקציות נפוצות של משתמשים שמשפרות את זמן הריצה של האפליקציה מההפעלה הראשונה. הקומפילציה המודרכת של AOT לא מסתמכת על מכשירי משתמשים, ואפשר לבצע אותה פעם אחת לכל גרסה במכונת פיתוח במקום במכשיר נייד. כשמשתמשים ב-Baseline Profile כדי לשלוח גרסאות, האופטימיזציות של האפליקציה זמינות הרבה יותר מהר מאשר כשמסתמכים רק על Cloud Profiles.

כשלא משתמשים בפרופיל בסיסי, כל קוד האפליקציה עובר קומפילציה JIT בזיכרון אחרי שהוא מפוענח, או שהוא נכתב לקובץ odex ברקע כשהמכשיר לא פעיל. אחרי התקנה או עדכון של אפליקציה, חוויית המשתמש לא אופטימלית בפעם הראשונה שהמשתמשים מפעילים אותה, עד שמבצעים אופטימיזציה של נתיבי קוד חדשים. אחרי האופטימיזציה, הרבה אפליקציות מראות שיפור של כ-30% בביצועים.

פרופילי הפעלה

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

שנתחיל?

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

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

  • פלאגין Android Gradle: ‏ com.android.tools.build:8.0.0
  • ספריית Macrobenchmark: androidx.benchmark:benchmark-macro-junit4:1.3.4
  • Profile Installer: androidx.profileinstaller:profileinstaller:1.4.1

מומלץ להשתמש בגרסה העדכנית של AGP כדי ליצור ולנהל פרופילים של Baseline. אלה הפונקציות העיקריות שזמינות בגרסאות שונות של AGP:

גרסת AGP תכונות
8.4 התקנות מקומיות של גרסאות build שלא ניתן לבצע בהן ניפוי באגים באמצעות כלי שורת הפקודה Gradle wrapper או Android Studio מתקינות פרופילים בסיסיים, כך שהביצועים של גרסת ה-build המקומית שלכם תואמים יותר לביצועים בסביבת הייצור. העדכון הזה לא משפיע על ביצועי הייצור של פרופילים בסיסיים.
8.3
  • תמיכה מלאה בספריית קבצים של מקורות (מודולים של ספריות): אפשר להצהיר על כמה קובצי מקור של פרופיל בסיסי, ולהשתמש בספריות שמותאמות לווריאציות, כמו src/free/generated/baselineProfiles/baseline-prof1.txt, עכשיו גם למודולים של ספריות וגם למודולים של אפליקציות.
  • פרופילים של Baseline כוללים desugared classes.
8.2
  • שכתוב כללים ב-R8:‏ D8 ו-R8 יכולים להמיר את הכללים של Baseline ושל Startup Profile שקריאים לאנשים, כדי לתעד באופן מלא את כל הכללים שנדרשים לכם כדי לשפר את ביצועי האפליקציה. הגדלה של הכיסוי של שיטות בפרופיל הבסיסי בכ-30% ושיפור הביצועים של האפליקציה בכ-15%.
  • פרופילים של הפעלה: יוצרים את הסוג החדש הזה של פרופיל בסיסי כדי לספק מידע על פריסת הקוד ב-DEX. משפר את ביצועי ההפעלה בעוד ‎~15%, או הרבה יותר באפליקציות גדולות.
‫8.0 הגרסה המומלצת המינימלית: אפשר להשתמש בפלאגין Baseline Profile Gradle כדי ליצור פרופילים של בסיס באמצעות משימת Gradle אחת.
  • תמיכה מלאה בספריית קבצים של מקורות (מודולים של אפליקציות): אפשר להצהיר על כמה קובצי מקור של פרופיל בסיסי ולהשתמש בספריות שמותאמות לווריאציות, כמו src/free/generated/baselineProfiles/baseline-prof1.txt.
7.4 הגרסה המינימלית הנתמכת: אפליקציות יכולות להשתמש בפרופילים בסיסיים מספריות, ולספק פרופיל בסיסי משלהן בקובץ src/main/baseline-prof.txt.
  • פרופילי בסיס נארזים בצורה נכונה כשיוצרים את ה-APK מ-App Bundle (בעיה מספר 230361284).
  • באפליקציות עם יותר מקובץ .dex אחד, פרופילי הבסיס נארזים בצורה נכונה עבור קובץ .dex הראשי.

דוגמה ליצירת פרופיל

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

@OptIn(ExperimentalBaselineProfilesApi::class)
class BaselineProfileGenerator {
    @get:Rule
    val baselineProfileRule = BaselineProfileRule()

    @Test
    fun appStartupAndUserJourneys() {
        baselineProfileRule.collect(packageName = PACKAGE_NAME) {
            // App startup journey.
            startActivityAndWait()

            device.findObject(By.text("COMPOSE LAZYLIST")).clickAndWait(Until.newWindow(), 1_000)
            device.findObject(By.res("myLazyColumn")).also {
                it.fling(Direction.DOWN)
                it.fling(Direction.UP)
            }
            device.pressBack()
        }
    }
}

אפשר לראות את הקוד הזה בהקשר מלא ובפירוט נוסף כחלק מדוגמאות הביצועים שלנו ב-GitHub.

הפרטים שצריך לכלול

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

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

ספריות יכולות לספק פרופילים משלהן של Baseline ולשלוח אותם עם גרסאות כדי לשפר את ביצועי האפליקציה. לדוגמה, אפשר לעיין בקטע Use a Baseline Profile במאמר Jetpack Compose performance.

איך פועלים פרופילי Baseline

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

  1. כללי הפרופיל שניתנים לקריאה על ידי בני אדם נוצרים עבור האפליקציה ומקומפלים לפורמט בינארי באפליקציה. אפשר למצוא אותם ב-assets/dexopt/baseline.prof. לאחר מכן אפשר להעלות את קובץ ה-AAB ל-Google Play כרגיל.

  2. מערכת Google Play מעבדת את הפרופיל ושולחת אותו ישירות למשתמשים יחד עם קובץ ה-APK. במהלך ההתקנה, ART מבצע הידור AOT של השיטות בפרופיל, וכתוצאה מכך השיטות האלה מופעלות מהר יותר. אם הפרופיל מכיל שיטות שמשמשות בהפעלת האפליקציה או במהלך רינדור של מסגרת, יכול להיות שזמני ההפעלה יהיו מהירים יותר והגמגום יפחת.

  3. התהליך הזה פועל בשיתוף עם צבירת פרופילים בענן כדי לשפר את הביצועים על סמך השימוש בפועל באפליקציה לאורך זמן.

איור 1. בתרשים הזה מוצג תהליך העבודה של פרופיל הבסיס, מההעלאה ועד למסירה למשתמש הקצה, ואיך תהליך העבודה הזה קשור לפרופילים ב-Cloud.

פרופילי ענן

פרופילים של Cloud מציעים סוג נוסף של PGO – פרופילים מצטברים מ-Google Play Store שמופצים לצורך קומפילציה בזמן ההתקנה – יחד עם פרופילים בסיסיים.

פרופילים בענן מבוססים על אינטראקציות של משתמשים בעולם האמיתי עם האפליקציה, אבל לוקח כמה שעות או ימים עד שהם מופצים אחרי עדכון, ולכן הזמינות שלהם מוגבלת. עד שהפרופילים יופצו באופן מלא, ביצועי האפליקציה לא יהיו אופטימליים למשתמשים באפליקציות חדשות או באפליקציות שעברו עדכון. בנוסף, פרופילים בענן תומכים רק במכשירי Android עם Android 9 (רמת API‏ 28) ומעלה, והם מתאימים רק לאפליקציות עם בסיס משתמשים גדול מספיק.

התנהגות הקומפילציה בגרסאות שונות של Android

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

גרסת Android שיטת ההרכבה גישת האופטימיזציה
‫5 עד 6 (רמת API‏ 21 עד 23) Full AOT האפליקציה כולה עוברת אופטימיזציה במהלך ההתקנה, ולכן זמני ההמתנה לשימוש באפליקציה ארוכים יותר, השימוש בזיכרון RAM ובשטח הדיסק גדל וזמני הטעינה של הקוד מהדיסק ארוכים יותר, מה שעלול להגדיל את זמני ההפעלה הקרה.
‫7 עד 8.1 (API ברמה 24 עד 27) ‫AOT חלקי (פרופיל Baseline) פרופילים בסיסיים מותקנים על ידי androidx.profileinstaller בהפעלה הראשונה, כשהמודול של האפליקציה מגדיר את התלות הזו. ‫ART יכול לשפר את זה עוד יותר על ידי הוספה של כללי פרופיל נוספים במהלך השימוש באפליקציה, וקומפילציה שלהם כשהמכשיר לא פעיל. האפשרות הזו מבצעת אופטימיזציה של שטח הדיסק ושל הזמן שנדרש לטעינת הקוד מהדיסק, וכך מקצרת את זמן ההמתנה של האפליקציה.
‫9 (רמת API‏ 28) ומעלה ‫AOT חלקי (Baseline + פרופיל ענן) ‫Play משתמש בפרופילים בסיסיים במהלך התקנות של אפליקציות כדי לבצע אופטימיזציה של חבילות ה-APK ושל פרופילים בענן – אם הם זמינים. אחרי ההתקנה, פרופילי ART מועלים ל-Play, נצברים ואז מסופקים כפרופילי Cloud למשתמשים אחרים כשהם מתקינים או מעדכנים את האפליקציה.

בעיות מוכרות

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

  • יכול להיות שייצור פרופיל בסיסי ייכשל בגלל הגדרות הרשאות בחלק מהמכשירים, כולל מכשירי OnePlus. כדי לעקוף את הבעיה, משביתים את האפשרות השבתת מעקב אחר הרשאות בהגדרות של אפשרויות למפתחים.

  • יצירת פרופיל בסיסי לא נתמכת במכשירים של Firebase Test Lab, כולל מכשירי Test Lab שמנוהלים על ידי Gradle (בעיה מספר 285187547).

  • כדי לספק פרופילים בסיסיים לספריות בהצלחה, צריך להשתמש בתוסף Baseline Profile Gradle בגרסה 1.2.3 או ב-AGP בגרסה 8.3 לפחות (בעיה מספר 313992099).

  • אם יוצרים פרופילים של קו בסיס באמצעות הפקודה ./gradlew app:generateBaselineProfile, גם מדדי ההשוואה במודול הבדיקה מופעלים, והתוצאות נמחקות. במקרה כזה, אפשר ליצור רק את פרופילי הבסיס על ידי הרצת הפקודה עם -P android.testInstrumentationRunnerArguments.androidx.benchmark.enabledRules=BaselineProfile. הבעיה הזו תוקנה ב-AGP 8.2.

  • הפקודה ליצירת פרופילים של Baseline לכל סוגי ה-build –‏ ./gradlew app:generateBaselineProfile – יוצרת פרופילים של Baseline רק לסוג ה-build של הגרסה. הבעיה הזו תוקנה ב-AGP 8.1.

  • יכול להיות שערוצי הפצה של אפליקציות שלא נמצאים בחנות Google Play לא יתמכו בשימוש בפרופילים בסיסיים בזמן ההתקנה. משתמשים באפליקציות שהותקנו דרך הערוצים האלה לא רואים את היתרונות עד שהתהליך dexopt פועל ברקע – מה שקורה בדרך כלל במהלך הלילה.

  • שיתוף פנימי של אפליקציות בחנות Play לא תומך בפרופילים בסיסיים, אבל מסלול הבדיקה הפנימית כן תומך.

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

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