R8 की मदद से ऐप्लिकेशन ऑप्टिमाइज़ेशन की सुविधा चालू करना

बेहतर उपयोगकर्ता अनुभव देने के लिए, आपको अपने ऐप्लिकेशन को ऑप्टिमाइज़ करना चाहिए, ताकि वह कम से कम साइज़ का हो और तेज़ी से काम करे. हमारा ऐप्लिकेशन ऑप्टिमाइज़र, जिसे R8 कहा जाता है, आपके ऐप्लिकेशन को बेहतर बनाता है. इसके लिए, वह इस्तेमाल न होने वाले कोड और संसाधनों को हटाता है, रनटाइम परफ़ॉर्मेंस को ऑप्टिमाइज़ करने के लिए कोड को फिर से लिखता है वगैरह. आपके उपयोगकर्ताओं के लिए, इसका मतलब है:

  • तेजी से शुरू कर सकते हैं
  • मेमोरी का इस्तेमाल कम होगा
  • रेंडरिंग और रनटाइम परफ़ॉर्मेंस बेहतर होगी
  • एएनआर की संख्या कम होगी

R8 ऑप्टिमाइज़ेशन की खास जानकारी

R8, आपके ऐप्लिकेशन को साइज़ और स्पीड के हिसाब से ऑप्टिमाइज़ करने के लिए, कई चरणों वाली प्रोसेस का इस्तेमाल करता है. मुख्य ऑपरेशन में ये शामिल हैं:

  • कोड छोटा करना (इसे ट्री शेकिंग भी कहा जाता है): R8, आपके ऐप्लिकेशन और उसकी लाइब्रेरी डिपेंडेंसी से, ऐसे कोड की पहचान करता है जिसे ऐक्सेस नहीं किया जा सकता. इसके बाद, उसे हटा देता है. R8, आपके ऐप्लिकेशन के एंट्री पॉइंट (जैसे, मेनिफ़ेस्ट में तय की गई Activities या Services) का विश्लेषण करके, रेफ़रंस वाले कोड का ग्राफ़ बनाता है. इसके बाद, ऐसे कोड को हटा देता है जिसका कोई रेफ़रंस नहीं होता.

  • लॉजिकल ऑप्टिमाइज़ेशन: R8, एक्ज़ीक्यूशन की क्षमता को बेहतर बनाने और ओवरहेड को कम करने के लिए, आपके कोड को फिर से लिखता है. मुख्य तकनीकों में ये शामिल हैं:

    • मेथड इनलाइनिंग: R8, मेथड कॉल साइट को, कॉल की गई मेथड के असल बॉडी से बदल देता है. इससे फ़ंक्शन कॉल का ओवरहेड खत्म हो जाता है. साथ ही, R8 को आगे ऑप्टिमाइज़ेशन करने की अनुमति मिलती है.

    • क्लास मर्जिंग: R8, क्लास और इंटरफ़ेस के सेट को एक क्लास में जोड़ देता है. इससे ऐप्लिकेशन में क्लास की संख्या कम हो जाती है. साथ ही, मेमोरी पर पड़ने वाला दबाव कम हो जाता है और स्टार्टअप की स्पीड बेहतर हो जाती है.

  • कोड को उलझाना (इसे काट-छांट की सुविधा भी कहा जाता है): DEX फ़ाइल का साइज़ कम करने के लिए, R8 क्लास, फ़ील्ड, और मेथड के नामों को छोटा कर देता है. उदाहरण के लिए, com.example.MyActivity को a.b.a बनाया जा सकता है.

Android Gradle प्लगिन (AGP) के 8.12.0 वर्शन के बाद से, R8, ऑप्टिमाइज़ेशन के चरणों के तहत संसाधनों को भी ऑप्टिमाइज़ करता है. ज़्यादा जानकारी के लिए, इस्तेमाल न किए जाने वाले ऑप्टिमाइज़ रिसॉर्स को हटाने की सुविधा लेख पढ़ें.

ऑप्टिमाइज़ेशन की सुविधा चालू करना

ऐप्लिकेशन ऑप्टिमाइज़ेशन की सुविधा चालू करने के लिए, अपने ऐप्लिकेशन की रिलीज़ बिल्ड's के ऐप्लिकेशन-लेवल के बिल्ड स्क्रिप्ट में, isMinifyEnabled = true (कोड ऑप्टिमाइज़ेशन के लिए) और isShrinkResources = true (संसाधन ऑप्टिमाइज़ेशन के लिए) सेट करें. यह सेटिंग, नीचे दिए गए कोड में दिखाई गई है. हमारा सुझाव है कि दोनों सेटिंग हमेशा चालू रखें. हमारा यह भी सुझाव है कि ऐप्लिकेशन ऑप्टिमाइज़ेशन की सुविधा, अपने ऐप्लिकेशन के सिर्फ़ उस फ़ाइनल वर्शन में चालू करें जिसे पब्लिश करने से पहले टेस्ट किया जाता है. आम तौर पर, यह रिलीज़ के लिए तैयार बिल्ड होता है. ऐसा इसलिए, क्योंकि ऑप्टिमाइज़ेशन से आपके प्रोजेक्ट का बिल्ड प्रोसेस में लगने वाला समय बढ़ जाता है. साथ ही, कोड में बदलाव करने के तरीके की वजह से, डीबग करना मुश्किल हो सकता है.

Kotlin

android {
    buildTypes {
        release {

            // Enables code-related app optimization.
            isMinifyEnabled = true

            // Enables resource shrinking.
            isShrinkResources = true

            proguardFiles(
                // Default file with automatically generated optimization rules.
                getDefaultProguardFile("proguard-android-optimize.txt"),

                ...
            )
            ...
        }
    }
    ...
}

शानदार

android {
    buildTypes {
        release {

            // Enables code-related app optimization.
            minifyEnabled = true

            // Enables resource shrinking.
            shrinkResources = true

            // Default file with automatically generated optimization rules.
            proguardFiles getDefaultProguardFile('proguard-android-optimize.txt')

            ...
        }
    }
}

R8 ऑप्टिमाइज़ेशन को बेहतर बनाना

R8 के परफ़ॉर्मेंस से जुड़े फ़ायदे, सीधे तौर पर इस बात पर निर्भर करते हैं कि R8, आपके कोड बेस को कितना ऑप्टिमाइज़ कर पाता है. R8 से ज़्यादा से ज़्यादा फ़ायदे पाने के लिए, सबसे सही तरीके अपनाएं:

कीप नियमों को बेहतर बनाने के लिए, R8 कॉन्फ़िगरेशन ऐनलाइज़र का इस्तेमाल करें.

R8 कॉन्फ़िगरेशन ऐनलाइज़र की मदद से ये काम किए जा सकते हैं:

  • R8 कॉन्फ़िगरेशन ऐनलाइज़र की रिपोर्ट में दी गई मेट्रिक की निगरानी करके, R8 के कॉन्फ़िगरेशन की कुल क्वालिटी को ट्रैक करें और उसे बेहतर बनाएं.
  • सबसे ज़्यादा कीप नियमों का पता लगाएं. ये नियम, ऑप्टिमाइज़ेशन को सबसे ज़्यादा रोकते हैं
  • और यह समझें कि ये नियम, किस तरह के ऑप्टिमाइज़ेशन को रोकते हैं, ताकि उन्हें बेहतर बनाया जा सके.

R8 कॉन्फ़िगरेशन ऐनलाइज़र, AGP के 9.3.0-alpha05 वर्शन या R8 के 9.3.7-dev वर्शन में उपलब्ध है. ज़्यादा जानकारी के लिए, R8 कॉन्फ़िगरेशन का विश्लेषण करना लेख पढ़ें.

इस्तेमाल न किए जाने वाले ऑप्टिमाइज़ रिसॉर्स को हटाने की सुविधा को ऑप्टिमाइज़ करना, ताकि ऐप्लिकेशन का साइज़ और भी कम हो सके

Android Gradle प्लगिन (AGP) के 8.12.0 वर्शन में, इस्तेमाल न किए जाने वाले ऑप्टिमाइज़ रिसॉर्स को हटाने की सुविधा जोड़ी गई है. इसका मकसद, संसाधन और कोड ऑप्टिमाइज़ेशन को इंटिग्रेट करना है, ताकि ऐप्लिकेशन का साइज़ और भी कम हो सके और वे तेज़ी से काम कर सकें.

इस्तेमाल न किए जाने वाले ऑप्टिमाइज़ रिसॉर्स को हटाने की सुविधा से पहले, Android Asset Packaging Tool (AAPT2), कीप नियम जनरेट करता था. इससे, संसाधन ऑप्टिमाइज़ेशन को कोड से अलग माना जाता था. इसलिए, अक्सर ऐसे कोड या संसाधन सुरक्षित रखे जाते थे जिन्हें ऐक्सेस नहीं किया जा सकता था. साथ ही, ये एक-दूसरे को रेफ़रंस करते थे.

इस्तेमाल न किए जाने वाले ऑप्टिमाइज़ रिसॉर्स को हटाने की सुविधा की मदद से, संसाधनों को प्रोग्राम कोड के हिस्से के तौर पर माना जाता है. इससे रेफ़रंस ग्राफ़ बनता है. जब कोड या संसाधनों के कलेक्शन का कोई रेफ़रंस नहीं होता, तो उसे कीप नियम के तहत सुरक्षित नहीं रखा जाता. साथ ही, उसे हटाया जा सकता है.

इस्तेमाल न किए जाने वाले ऑप्टिमाइज़ रिसॉर्स को हटाने की सुविधा चालू करना

AGP 8.12 या 8.13 के लिए, इस्तेमाल न किए जाने वाले ऑप्टिमाइज़ रिसॉर्स को हटाने की नई पाइपलाइन चालू करने के लिए, अपने प्रोजेक्ट की gradle.properties फ़ाइल में यह कोड जोड़ें:

android.r8.optimizedResourceShrinking=true

अगर AGP 9.0.0 या नया वर्शन इस्तेमाल किया जा रहा है, तो आपको android.r8.optimizedResourceShrinking=true सेट करने की ज़रूरत नहीं है. जब आपके बिल्ड कॉन्फ़िगरेशन में isShrinkResources = true चालू होता है, तो इस्तेमाल न किए जाने वाले ऑप्टिमाइज़ रिसॉर्स को हटाने की सुविधा अपने-आप लागू हो जाती है.

R8 ऑप्टिमाइज़ेशन सेटिंग की पुष्टि करना और उन्हें कॉन्फ़िगर करना

R8 को ऑप्टिमाइज़ेशन की पूरी क्षमता का इस्तेमाल करने की अनुमति देने के लिए, अपने प्रोजेक्ट की gradle.properties फ़ाइल से यह लाइन हटाएं. हालांकि, ऐसा सिर्फ़ तब करें, जब यह लाइन मौजूद हो:

android.enableR8.fullMode=false # Remove this line from your codebase.

ध्यान दें कि ऐप्लिकेशन ऑप्टिमाइज़ेशन की सुविधा चालू करने से, स्टैक ट्रेस को समझना मुश्किल हो जाता है. ऐसा तब होता है, जब R8 क्लास या मेथड के नाम बदल देता है. अपने सोर्स कोड से सही तरीके से मेल खाने वाले स्टैक ट्रेस पाने के लिए, ओरिजनल स्टैक ट्रेस वापस पाना लेख पढ़ें.

अगर R8 चालू है, तो आपको स्टार्टअप की परफ़ॉर्मेंस को और बेहतर बनाने के लिए, स्टार्टअप प्रोफ़ाइल भी बनानी चाहिए.

अगर ऐप्लिकेशन ऑप्टिमाइज़ेशन की सुविधा चालू करने पर गड़बड़ियां होती हैं, तो उन्हें ठीक करने के लिए ये रणनीतियां अपनाएं:

अगर आपको अपने बिल्ड की स्पीड को ऑप्टिमाइज़ करना है, तो R8 को अपने एनवायरमेंट के हिसाब से कॉन्फ़िगर करने के तरीके के बारे में जानने के लिए, R8 को चलाने का तरीका कॉन्फ़िगर करना लेख पढ़ें.

AGP और R8 के वर्शन के व्यवहार में बदलाव

यहां दी गई टेबल में, Android Gradle प्लगिन (AGP) और R8 कंपाइलर के अलग-अलग वर्शन में जोड़ी गई मुख्य सुविधाओं के बारे में बताया गया है.

AGP का वर्शन जोड़ी गई सुविधाएं
9.1 क्लास को डिफ़ॉल्ट रूप से रीपैकेज किया जाता है: R8, क्लास को रीपैकेज करता है. इसके लिए, वह क्लास को बिना नाम वाले पैकेज में, टॉप लेवल पर ले जाता है, ताकि DEX को और कंपैक्ट किया जा सके. इससे -repackageclasses विकल्प तय करने की ज़रूरत नहीं होती. यह सुविधा कैसे काम करती है और इससे ऑप्ट आउट करने का तरीका जानने के लिए, ग्लोबल विकल्प लेख पढ़ें.
9.0 इस्तेमाल न किए जाने वाले ऑप्टिमाइज़ रिसॉर्स को हटाने की सुविधा: यह सुविधा डिफ़ॉल्ट रूप से चालू होती है. इसे android.r8.optimizedResourceShrinking का इस्तेमाल करके कंट्रोल किया जाता है. इस्तेमाल न किए जाने वाले ऑप्टिमाइज़ रिसॉर्स को हटाने की सुविधा, संसाधन ऑप्टिमाइज़ेशन को कोड ऑप्टिमाइज़ेशन पाइपलाइन के साथ इंटिग्रेट करने में मदद करती है. इससे ऐप्लिकेशन का साइज़ कम होता है और वे तेज़ी से काम करते हैं. कोड और संसाधन रेफ़रंस, दोनों को एक साथ ऑप्टिमाइज़ करके, यह उन संसाधनों की पहचान करता है और उन्हें हटाता है जिन्हें सिर्फ़ इस्तेमाल न होने वाले कोड से रेफ़रंस किया जाता है. यह, पहले की अलग-अलग ऑप्टिमाइज़ेशन प्रोसेस से काफ़ी बेहतर है.

यह सुविधा, उन ऐप्लिकेशन के लिए खास तौर पर काम की है जो अलग-अलग फ़ॉर्म फ़ैक्टर वर्टिकल में, ज़्यादातर संसाधन और कोड शेयर करते हैं. इससे ऐप्लिकेशन के साइज़ में 50% से ज़्यादा की कमी देखी गई है. साइज़ में कमी होने से, ऐप्लिकेशन कम समय में डाउनलोड और इंस्टॉल होते हैं. साथ ही, स्टार्टअप की स्पीड बेहतर होती है, रेंडरिंग बेहतर होती है, और एएनआर की संख्या कम होती है. इससे उपयोगकर्ता अनुभव बेहतर होता है.

लाइब्रेरी के नियम फ़िल्टर करना: लाइब्रेरी के उपभोक्ता नियमों में, ग्लोबल विकल्पों (उदाहरण के लिए, -dontobfuscate) के लिए सहायता बंद कर दी गई है. साथ ही, ऐप्लिकेशन इन्हें फ़िल्टर कर देंगे. ज़्यादा जानकारी के लिए, ग्लोबल विकल्प जोड़ना लेख पढ़ें.

Kotlin के शून्य वैल्यू की जांच: यह सुविधा डिफ़ॉल्ट रूप से ऑप्टिमाइज़ की गई है. इसे -processkotlinnullchecks का इस्तेमाल करके कंट्रोल किया जाता है. इस वर्शन में, बिल्ड की स्पीड में भी काफ़ी सुधार किया गया है. ज़्यादा जानकारी के लिए, अतिरिक्त ऑप्टिमाइज़ेशन के लिए ग्लोबल विकल्प लेख पढ़ें.

चुनिंदा पैकेज ऑप्टिमाइज़ करना: चुनिंदा पैकेज ऑप्टिमाइज़ करने के लिए, packageScope का इस्तेमाल किया जा सकता है. यह सुविधा, एक्सपेरिमेंट के तौर पर उपलब्ध है. ज़्यादा जानकारी के लिए, तय किए गए पैकेज को packageScope की मदद से ऑप्टिमाइज़ करना लेख पढ़ें.

डिफ़ॉल्ट रूप से ऑप्टिमाइज़ किया गया: getDefaultProguardFile("proguard-android.txt") के लिए सहायता बंद कर दी गई है, क्योंकि इसमें -dontoptimize शामिल है. इसका इस्तेमाल नहीं करना चाहिए. इसके बजाय, "proguard-android-optimize.txt" का इस्तेमाल करें. अगर आपको अपने ऐप्लिकेशन में, ग्लोबल तौर पर ऑप्टिमाइज़ेशन की सुविधा बंद करनी है, तो proguard फ़ाइल में फ़्लैग को मैन्युअल तरीके से जोड़ें.
8.12 इस्तेमाल न किए जाने वाले ऑप्टिमाइज़ रिसॉर्स को हटाने की सुविधा: शुरुआती सहायता जोड़ी गई. इसे android.r8.optimizedResourceShrinking का इस्तेमाल करके कंट्रोल किया जाता है. इस्तेमाल न किए जाने वाले ऑप्टिमाइज़ रिसॉर्स को हटाने की सुविधा, संसाधन ऑप्टिमाइज़ेशन को कोड ऑप्टिमाइज़ेशन पाइपलाइन के साथ इंटिग्रेट करने में मदद करती है. आपको AGP के इस वर्शन में, इसे मैन्युअल तरीके से चालू करना होगा.

Logcat में स्टैक ट्रेस वापस लाना: Android Studio के Logcat विंडो में, स्टैक ट्रेस को अपने-आप वापस लाने की सुविधा के लिए सहायता जोड़ी गई.
8.6 स्टैक ट्रेस को वापस लाने की सुविधा बेहतर हुई: इसमें सभी minSdk लेवल के लिए, फ़ाइल नाम और लाइन नंबर के स्टैक ट्रेस को डिफ़ॉल्ट रूप से शामिल किया गया है. इससे पहले, वर्शन 8.2 में minSdk 26 या इससे ज़्यादा की ज़रूरत होती थी.

R8 को अपडेट करने से, यह पक्का करने में मदद मिलती है कि कोड को उलझाने के बाद बनाए गए बिल्ड के स्टैक ट्रेस, आसानी से और साफ़ तौर पर पढ़े जा सकें. इस वर्शन में, लाइन नंबर और सोर्स फ़ाइलों को मैप करने का तरीका बेहतर बनाया गया है. इससे Android Studio Logcat जैसे टूल के लिए, क्रैश को ओरिजनल सोर्स कोड में अपने-आप वापस लाना आसान हो जाता है.
8.0 डिफ़ॉल्ट रूप से फ़ुल मोड: R8 का फ़ुल मोड, ऑप्टिमाइज़ेशन की ज़्यादा बेहतर सुविधा देता है. यह सुविधा डिफ़ॉल्ट रूप से चालू होती है. android.enableR8.fullMode=false का इस्तेमाल करके, इससे ऑप्ट आउट किया जा सकता है.
7.0 फ़ुल मोड उपलब्ध: इसे android.enableR8.fullMode=true का इस्तेमाल करके, ऑप्ट-इन सुविधा के तौर पर जोड़ा गया है. फ़ुल मोड, आपके कोड में रिफ़्लेक्शन और अन्य डाइनैमिक सुविधाओं के इस्तेमाल के बारे में ज़्यादा सख्त अनुमान लगाकर, ऑप्टिमाइज़ेशन की ज़्यादा बेहतर सुविधा देता है. इससे ऐप्लिकेशन का साइज़ कम होता है और परफ़ॉर्मेंस बेहतर होती है. हालांकि, ज़रूरी कोड को हटाने से रोकने के लिए, इसमें कीप नियम जोड़ने पड़ सकते हैं.