काम करने के तरीके में बदलाव: Android 17 या इसके बाद के वर्शन को टारगेट करने वाले ऐप्लिकेशन

Android के पिछले वर्शन की तरह ही, Android 17 में भी काम करने के तरीके में कुछ बदलाव किए गए हैं. इनसे आपके ऐप्लिकेशन पर असर पड़ सकता है. काम करने के तरीके में किए गए ये बदलाव, सिर्फ़ उन ऐप्लिकेशन पर लागू होते हैं जो Android 17 या इसके बाद के वर्शन को टारगेट करते हैं. अगर आपका ऐप्लिकेशन Android 17 या इसके बाद के वर्शन को टारगेट करता है, तो आपको अपने ऐप्लिकेशन में बदलाव करना चाहिए, ताकि वह इन बदलावों के मुताबिक काम कर सके.

Android 17 पर काम करने वाले सभी ऐप्लिकेशन पर असर डालने वाले बदलावों की सूची भी देखें. इससे कोई फ़र्क़ नहीं पड़ता कि आपके ऐप्लिकेशन का targetSdkVersion क्या है.

उपयोगकर्ता अनुभव और सिस्टम यूज़र इंटरफ़ेस (यूआई)

Android 17 में ये बदलाव शामिल हैं. इनका मकसद, उपयोगकर्ताओं को ज़्यादा बेहतर और आसान अनुभव देना है.

मेमोरी की सीमा वाला विजेट

Android 17 से, सिस्टम Android 17 (एपीआई लेवल 37) या इसके बाद के वर्शन को टारगेट करने वाले ऐप्लिकेशन के लिए, RemoteViews अपडेट पर मेमोरी की तय सीमा को सख्ती से लागू करता है. जब कोई ऐप्लिकेशन RemoteViews ऑब्जेक्ट को AppWidgetManager.updateAppWidget को पास करता है, तो system_server पेलोड में हर ओरिएंटेशन और साइज़ बकेट में मौजूद सभी इमेज डेटा के कुल मेमोरी फ़ुटप्रिंट का हिसाब लगाता है. अगर कुल मेमोरी, सिस्टम की तय सीमा (mMaxWidgetBitmapMemory) से ज़्यादा हो जाती है, तो सिस्टम अपडेट को अस्वीकार कर देता है और IllegalArgumentException दिखाता है:

java.lang.IllegalArgumentException: RemoteViews for widget update exceeds maximum bitmap memory usage (used: XXXXX, max: YYYYY)

एपीआई लेवल 36 या इससे पहले के लेवल को टारगेट करने वाले ऐप्लिकेशन के लिए, सिस्टम मेमोरी के इस उल्लंघन को चेतावनी (Slog.w) के तौर पर लॉग करता है. हालांकि, इसके लिए कोई अपवाद नहीं दिखाता.

सिस्टम, मेमोरी की सीमा का हिसाब कैसे लगाता है

सिस्टम, चालू डिसप्ले कॉन्फ़िगरेशन के लिए, विजेट बिटमैप मेमोरी बजट को 6 * width * height बाइट पर सेट करता है. यह 1.5 * 4 * width * height के बराबर है, जो फ़ुल-स्क्रीन ARGB_8888 बफ़र के साइज़ का 1.5 गुना है. एपीआई लेवल 37 और इसके बाद के वर्शन में, इस कैलकुलेशन में ये दोनों शामिल हैं:

  • RemoteViews.mBitmapCache में सेव किए गए, इन-मेमोरी Bitmap और बिटमैप-बैक्ड Icon ऑब्जेक्ट (Icon.TYPE_BITMAP और Icon.TYPE_ADAPTIVE_BITMAP). जैसे, setImageViewBitmap, Icon.createWithBitmap, Icon.createWithAdaptiveBitmap या Jetpack Glance ImageProvider(bitmap) को किए गए कॉल. mBitmapCache में मौजूद हर यूनीक Bitmap या बिटमैप-बैक्ड Icon इंस्टेंस को RemoteViews की हैरारकी के हिसाब से एक बार गिना जाता है.
  • यूआरआई पर आधारित इमेज (Icon.createWithContentUri, setImageViewUri या Glance ImageProvider(uri)), system_server में RemoteViews आईपीसी बाइट की सीमा में नहीं गिनी जाती हैं. हालांकि, विजेट होस्ट प्रोसेस, रेफ़रंस के तौर पर दी गई content:// फ़ाइल को फ़ुल रिज़ॉल्यूशन में डिकोड करके, अपने हीप में सेव करती है. FileProvider यूआरआई के ज़रिए इमेज को दिखाने से पहले, डाउनसैंपल की गई इमेज को हमेशा context.cacheDir में लिखें.

जोखिम कम करने के तरीके

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

  1. WindowMetrics से रनटाइम मेमोरी बजट का हिसाब लगाएं: एपीआई लेवल 30 और इसके बाद के वर्शन पर, resources.displayMetrics के बजाय WindowManager.currentWindowMetrics.bounds से ऐक्टिव विंडो की सीमाएं पढ़ें. मल्टी-रिज़ॉल्यूशन और फ़ोल्ड किए जा सकने वाले डिवाइसों पर, displayMetrics बंद डिसप्ले के डाइमेंशन की जानकारी दे सकता है. विजेट इमेज के लिए कुल बजट का अनुमान 6L * bounds.width() * bounds.height() लगाएं, जैसा कि इस उदाहरण में दिखाया गया है:

    private const val FALLBACK_MAX_BYTES = 15_000_000L
    
    fun calculateWidgetMemoryCapBytes(context: Context): Long {
        if (Build.VERSION.SDK_INT >= Build.VERSION_CODES.R) {
            val wm = context.getSystemService(WindowManager::class.java)
                ?: return FALLBACK_MAX_BYTES
            val bounds = wm.currentWindowMetrics.bounds
            return 6L * bounds.width().toLong() * bounds.height().toLong()
        }
        val dm = context.resources.displayMetrics
        return 6L * dm.widthPixels.toLong() * dm.heightPixels.toLong()
    }
    
  2. इमेज को डाउनसैंपल करके, विजेट के दिखने वाले डाइमेंशन के हिसाब से बनाएं और RGB_565 का इस्तेमाल करें: विजेट के ज़्यादा से ज़्यादा डिसप्ले डाइमेंशन (maxWidthDp x maxHeightDp) के हिसाब से, बिट मैप को दो की घात वाली BitmapFactory.Options.inSampleSize वैल्यू के साथ डिकोड करें. साथ ही, अपारदर्शी फ़ोटो और थंबनेल के लिए, ARGB_8888 (4 बाइट प्रति पिक्सल) के बजाय Bitmap.Config.RGB_565 (2 बाइट प्रति पिक्सल) का इस्तेमाल करें.

  3. Jetpack Glance में provideContent के बाहर बिटमैप डिकोडिंग को होस्ट करना: SizeMode.Responsive या SizeMode.Exact का इस्तेमाल करने पर, Glance हर साइज़ बकेट के लिए एक बार आपके provideContent लैम्डा को शुरू करता है. provideGlance में हर शेयर किए गए Bitmap को एक बार डिकोड करें. ऐसा provideContent को कॉल करने से पहले करें, ताकि सभी साइज़ बकेट, RemoteViews.mBitmapCache में मौजूद एक ही Bitmap इंस्टेंस को रेफ़र करें.

  4. इमेज बदलते समय, फ़ुल updateAppWidget कॉल का इस्तेमाल करें: क्लासिक AppWidgetProvider लागू करने के दौरान, Bitmap या Icon व्यू को स्वैप करने के लिए, AppWidgetManager.partiallyUpdateAppWidget को कॉल करने से बचें. आंशिक अपडेट, system_server में मौजूद RemoteViews ट्री में नई कार्रवाइयों को मर्ज करते हैं. इसके लिए, पहले से कैश मेमोरी में सेव की गई इमेज की कार्रवाइयों को नहीं हटाया जाता. इसके बजाय, पूरा RemoteViews लेआउट बनाएं और updateAppWidget को कॉल करें.

  5. गड़बड़ी होने पर फ़ॉलबैक लेआउट उपलब्ध कराना: Jetpack Glance में, onCompositionError को बदलें, ताकि अपडेट न होने पर, ज़ीरो-बिटमैप RemoteViews फ़ॉलबैक रेंडर किया जा सके.

कनेक्ट किए गए किसी डिवाइस पर, अपने विजेट की मौजूदा सीरियलाइज़ की गई बिट मैप मेमोरी के इस्तेमाल की जांच की जा सकती है. इसके लिए, यह तरीका अपनाएं:

adb shell dumpsys appwidget

मुख्य फ़ंक्शन

Android 17 में ये बदलाव शामिल हैं. इनसे Android सिस्टम की कई मुख्य सुविधाओं में बदलाव किया जाता है या उन्हें बेहतर बनाया जाता है.

MessageQueue को लॉक-फ़्री तरीके से लागू करने की नई सुविधा

Android 17 से, Android 17 (एपीआई लेवल 37) या इसके बाद के वर्शन को टारगेट करने वाले ऐप्लिकेशन को android.os.MessageQueue का नया लॉक-फ़्री इंप्लिमेंटेशन मिलता है. इस नए तरीके से परफ़ॉर्मेंस बेहतर होती है और फ़्रेम छूटने की समस्या कम होती है. हालांकि, इससे उन क्लाइंट पर असर पड़ सकता है जो MessageQueue के निजी फ़ील्ड और तरीकों का इस्तेमाल करते हैं.

ज़्यादा जानकारी के लिए, MessageQueue के काम करने के तरीके में हुए बदलाव से जुड़े दिशा-निर्देश देखें. इसमें जोखिम कम करने की रणनीतियां भी शामिल हैं.

स्टैटिक फ़ाइनल फ़ील्ड में अब बदलाव नहीं किया जा सकता

Android 17 या इसके बाद के वर्शन पर चलने वाले और Android 17 (एपीआई लेवल 37) या इसके बाद के वर्शन को टारगेट करने वाले ऐप्लिकेशन, static final फ़ील्ड में बदलाव नहीं कर सकते. अगर कोई ऐप्लिकेशन, रिफ़्लेक्शन का इस्तेमाल करके static final फ़ील्ड में बदलाव करने की कोशिश करता है, तो इससे IllegalAccessException होगा. जेएनआई एपीआई (जैसे कि SetStaticLongField()) का इस्तेमाल करके, इनमें से किसी फ़ील्ड में बदलाव करने की कोशिश करने पर, ऐप्लिकेशन क्रैश हो जाएगा.

सुलभता

Android 17 में, सुलभता को बेहतर बनाने के लिए ये बदलाव किए गए हैं.

आईएमई के जटिल फ़िज़िकल कीबोर्ड से टाइपिंग के लिए सुलभता सहायता

इस सुविधा में, नए AccessibilityEvent और TextAttribute एपीआई जोड़े गए हैं. इनसे सीजेकेवी भाषाओं में इनपुट के लिए, स्क्रीन रीडर के बोलकर दिए जाने वाले जवाब को बेहतर बनाया जा सकता है. CJKV IME ऐप्लिकेशन अब यह सिग्नल दे सकते हैं कि टेक्स्ट कंपोज़िशन के दौरान, टेक्स्ट कन्वर्ज़न कैंडिडेट को चुना गया है या नहीं. टेक्स्ट में बदलाव करने की सुविधा वाले ऐप्लिकेशन, टेक्स्ट में बदलाव करने से जुड़े सुलभता इवेंट भेजते समय, टेक्स्ट में बदलाव करने के टाइप तय कर सकते हैं. उदाहरण के लिए, ऐप्लिकेशन यह बता सकते हैं कि टेक्स्ट कंपोज़िशन के दौरान टेक्स्ट में बदलाव हुआ है या किसी कमिट की वजह से टेक्स्ट में बदलाव हुआ है. ऐसा करने से, स्क्रीन रीडर जैसी सुलभता सेवाएं, टेक्स्ट में किए गए बदलाव के आधार पर ज़्यादा सटीक सुझाव दे पाती हैं.

Android SDK इस्तेमाल करने वाले ऐप्लिकेशन की संख्या

  • आईएमई ऐप्लिकेशन: बदलाव करने वाले फ़ील्ड में टेक्स्ट सेट करते समय, आईएमई TextAttribute.Builder.setTextSuggestionSelected() का इस्तेमाल करके यह बता सकते हैं कि कन्वर्ज़न के लिए कोई खास कैंडिडेट चुना गया था या नहीं.

  • एडिट फ़ील्ड वाले ऐप्लिकेशन: कस्टम InputConnection को बनाए रखने वाले ऐप्लिकेशन, TextAttribute.isTextSuggestionSelected() को कॉल करके, चुने गए कैंडिडेट का डेटा वापस पा सकते हैं. इसके बाद, इन ऐप्लिकेशन को TYPE_VIEW_TEXT_CHANGED इवेंट भेजते समय AccessibilityEvent.setTextChangeTypes() को कॉल करना चाहिए. Android 17 (एपीआई लेवल 37) को टारगेट करने वाले और स्टैंडर्ड TextView का इस्तेमाल करने वाले ऐप्लिकेशन के लिए, यह सुविधा डिफ़ॉल्ट रूप से चालू होगी. (इसका मतलब है कि सुलभता सेवाओं को इवेंट भेजते समय, TextView आईएमई से डेटा वापस पाने और टेक्स्ट में बदलाव के टाइप सेट करने का काम करेगा).

  • सुलभता सेवाएं: TYPE_VIEW_TEXT_CHANGED इवेंट को प्रोसेस करने वाली सुलभता सेवाएं, AccessibilityEvent.getTextChangeTypes() को कॉल कर सकती हैं. इससे बदलाव की प्रकृति की पहचान की जा सकती है और उसके हिसाब से सुझाव देने की रणनीतियों में बदलाव किया जा सकता है.

निजता

Android 17 में, उपयोगकर्ता की निजता को बेहतर बनाने के लिए ये बदलाव किए गए हैं.

ईसीएच (एन्क्रिप्ट किया गया ClientHello) चालू है

Android 17 में, एन्क्रिप्ट (सुरक्षित) किए गए ClientHello (ईसीएच) के लिए प्लैटफ़ॉर्म सपोर्ट की सुविधा जोड़ी गई है. यह एक टीएलएस एक्सटेंशन है, जो टीएलएस हैंडशेक में सर्वर नेम इंडिकेशन (एसएनआई) को एन्क्रिप्ट करके, उपयोगकर्ता की निजता को बेहतर बनाता है. एन्क्रिप्ट करने के इस तरीके से, नेटवर्क पर नज़र रखने वाले लोगों को उस डोमेन की पहचान करने में मुश्किल होती है जिससे आपका ऐप्लिकेशन कनेक्ट हो रहा है.

Android 17 (एपीआई लेवल 37) या इसके बाद के वर्शन को टारगेट करने वाले ऐप्लिकेशन के लिए, टीएलएस कनेक्शन के लिए ईसीएच का इस्तेमाल किया जाता है. ईसीएच सिर्फ़ तब चालू होता है, जब ऐप्लिकेशन में इस्तेमाल की गई नेटवर्किंग लाइब्रेरी (उदाहरण के लिए, HttpEngine, WebView या OkHttp) में ईसीएच की सुविधा इंटिग्रेट की गई हो. साथ ही, रिमोट सर्वर भी ईसीएच प्रोटोकॉल के साथ काम करता हो. अगर ईसीएच के लिए बातचीत नहीं की जा सकती, तो क्लाइंट, रैंडम कॉन्टेंट के साथ ईसीएच एक्सटेंशन भेजता है. इस तरीके को ईसीएच ग्रीस कहा जाता है. ईसीएच ग्रीस के काम करने के तरीके के बारे में ज़्यादा जानने के लिए, आरएफ़सी 9849 देखें.

ऐप्लिकेशन को इस व्यवहार को पसंद के मुताबिक बनाने की अनुमति देने के लिए, Android 17 में नेटवर्क की सुरक्षा से जुड़े कॉन्फ़िगरेशन की फ़ाइल में एक नया <domainEncryption> एलिमेंट जोड़ा गया है. डेवलपर, <base-config> या <domain-config> टैग में <domainEncryption> का इस्तेमाल करके, ग्लोबल या हर डोमेन के हिसाब से ईसीएच मोड (उदाहरण के लिए, "enabled" या "disabled") चुन सकते हैं.

ज़्यादा जानकारी के लिए, एन्क्रिप्ट किया गया क्लाइंट हेलो दस्तावेज़ देखें.

Android 17 को टारगेट करने वाले ऐप्लिकेशन के लिए, लोकल नेटवर्क ऐक्सेस करने की अनुमति ज़रूरी है

Android 17 में, ACCESS_LOCAL_NETWORK रनटाइम की अनुमति जोड़ी गई है. इससे उपयोगकर्ताओं को लोकल नेटवर्क के अनधिकृत ऐक्सेस से सुरक्षित रखने में मदद मिलती है. यह अनुमति, NEARBY_DEVICES के मौजूदा अनुमतियों के समूह के तहत आती है. इसलिए, जिन उपयोगकर्ताओं ने पहले ही NEARBY_DEVICES की अन्य अनुमतियां दी हैं उनसे दोबारा अनुमति नहीं मांगी जाती. इस नई शर्त की वजह से, नुकसान पहुंचाने वाले ऐप्लिकेशन, लोकल नेटवर्क के ऐक्सेस का गलत इस्तेमाल नहीं कर पाते. इससे वे उपयोगकर्ता को ट्रैक नहीं कर पाते और उसका फ़िंगरप्रिंट नहीं ले पाते. इस अनुमति का एलान और अनुरोध करने पर, आपका ऐप्लिकेशन लोकल एरिया नेटवर्क (लैन) पर मौजूद डिवाइसों को ढूंढ सकता है और उनसे कनेक्ट कर सकता है. जैसे, स्मार्ट होम डिवाइस या कास्टिंग रिसीवर.

Android 17 (एपीआई लेवल 37) या इसके बाद के वर्शन को टारगेट करने वाले ऐप्लिकेशन के पास, अब एलएएन डिवाइसों के साथ कम्यूनिकेशन बनाए रखने के दो तरीके हैं: सिस्टम की मदद से काम करने वाले और निजता बनाए रखने वाले डिवाइस पिकर का इस्तेमाल करें, ताकि अनुमति मांगने वाला प्रॉम्प्ट न दिखे. इसके अलावा, लोकल नेटवर्क कम्यूनिकेशन बनाए रखने के लिए, रनटाइम के दौरान इस नई अनुमति का अनुरोध करें.

ज़्यादा जानकारी के लिए, लोकल नेटवर्क की अनुमति से जुड़ा दस्तावेज़ देखें.

फ़िज़िकल डिवाइसों से पासवर्ड छिपाना

अगर कोई ऐप्लिकेशन Android 17 (एपीआई लेवल 37) या इसके बाद के वर्शन को टारगेट करता है और उपयोगकर्ता किसी फ़िज़िकल इनपुट डिवाइस (उदाहरण के लिए, कोई बाहरी कीबोर्ड) का इस्तेमाल कर रहा है, तो Android ऑपरेटिंग सिस्टम, पासवर्ड फ़ील्ड में मौजूद सभी वर्णों पर नई show_passwords_physical सेटिंग लागू करता है. डिफ़ॉल्ट रूप से, यह सेटिंग पासवर्ड के सभी वर्णों को छिपा देती है.

Android सिस्टम, पासवर्ड के आखिरी वर्ण को दिखाता है, ताकि उपयोगकर्ता यह देख सके कि उसने पासवर्ड गलत तो नहीं डाला है. हालांकि, बड़े बाहरी कीबोर्ड के साथ इसकी ज़रूरत बहुत कम होती है. इसके अलावा, बाहरी कीबोर्ड वाले डिवाइसों में अक्सर बड़े डिसप्ले होते हैं. इससे, टाइप किए गए पासवर्ड को किसी व्यक्ति के देखने का खतरा बढ़ जाता है.

अगर उपयोगकर्ता डिवाइस की टचस्क्रीन का इस्तेमाल कर रहा है, तो सिस्टम नई show_passwords_touch सेटिंग लागू करता है.

स्टैंडर्ड एसएमएस के लिए ओटीपी से सुरक्षा

Android 17 से, Android अपनी एसएमएस ओटीपी सुरक्षा सुविधा को स्टैंडर्ड एसएमएस मैसेज पर भी लागू कर रहा है. ये ऐसे एसएमएस मैसेज होते हैं जिनमें ओटीपी होता है, लेकिन वे WebOTP या एसएमएस रिट्रीवर फ़ॉर्मैट का इस्तेमाल नहीं करते. Android 17 (एपीआई लेवल 37) या इसके बाद के वर्शन को टारगेट करने वाले ज़्यादातर ऐप्लिकेशन के लिए, ये एसएमएस मिलने के तीन घंटे बाद तक उपलब्ध नहीं होते. इस देरी का मकसद, ओटीपी को हाइजैक होने से रोकना है. इस तीन घंटे की देरी के दौरान, SMS_RECEIVED_ACTION ब्रॉडकास्ट को रोक दिया जाता है और एसएमएस सेवा देने वाली कंपनी के डेटाबेस की क्वेरी फ़िल्टर की जाती हैं. देरी के बाद, इन ऐप्लिकेशन के लिए एसएमएस उपलब्ध हो जाता है.

कुछ ऐप्लिकेशन को इस देरी से छूट दी गई है. जैसे, डिफ़ॉल्ट एसएमएस सहायक ऐप्लिकेशन, कनेक्ट किए गए डिवाइस के कंपैनियन ऐप्लिकेशन वगैरह. ओटीपी निकालने के लिए, एसएमएस पढ़ने की सुविधा पर निर्भर सभी ऐप्लिकेशन को SMS Retriever या SMS User Consent एपीआई का इस्तेमाल करना चाहिए. इससे यह पक्का किया जा सकेगा कि ऐप्लिकेशन की सुविधा लगातार काम करती रहे.

सुरक्षा

Android 17 में, डिवाइस और ऐप्लिकेशन की सुरक्षा के लिए ये सुधार किए गए हैं.

गतिविधि की सुरक्षा

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

डेवलपर पर पड़ने वाले मुख्य असर:

  • बीएएल को बेहतर बनाना और ऑप्ट-इन करने की सुविधा को बेहतर बनाना: हम बैकग्राउंड ऐक्टिविटी लॉन्च (बीएएल) से जुड़ी पाबंदियों को बेहतर बना रहे हैं. इसके लिए, हम IntentSender के लिए सुरक्षा सुविधाओं को बढ़ा रहे हैं. डेवलपर को लेगसी MODE_BACKGROUND_ACTIVITY_START_ALLOWED कॉन्सटैंट से माइग्रेट करना होगा. इसके बजाय, आपको MODE_BACKGROUND_ACTIVITY_START_ALLOW_IF_VISIBLE जैसे बेहतर कंट्रोल अपनाने चाहिए. इससे गतिविधि सिर्फ़ तब शुरू होती है, जब कॉलिंग ऐप्लिकेशन दिखता है. इससे हमले की जगह काफ़ी कम हो जाती है.
  • अपनाने के लिए टूल: डेवलपर को स्ट्रिक्ट मोड और अपडेट की गई लिंट जांचों का इस्तेमाल करना चाहिए, ताकि वे लेगसी पैटर्न की पहचान कर सकें. साथ ही, यह पक्का कर सकें कि वे आने वाले समय में टारगेट एसडीके की ज़रूरी शर्तों को पूरा करने के लिए तैयार हैं.

सीटी को डिफ़ॉल्ट रूप से चालू करें

अगर कोई ऐप्लिकेशन Android 17 (एपीआई लेवल 37) या इसके बाद के वर्शन को टारगेट करता है, तो प्रमाणपत्र पारदर्शिता (सीटी) की सुविधा डिफ़ॉल्ट रूप से चालू होती है. (Android 16 पर सीटी की सुविधा उपलब्ध है, लेकिन ऐप्लिकेशन को इसके लिए ऑप्ट इन करना होगा.)

Safer Native DCL—C

अगर आपका ऐप्लिकेशन Android 17 (एपीआई लेवल 37) या इसके बाद के वर्शन को टारगेट करता है, तो DEX और JAR फ़ाइलों के लिए Android 14 में पेश की गई, डाइनैमिक कोड लोडिंग (डीसीएल) की ज़्यादा सुरक्षित सुविधा अब नेटिव लाइब्रेरी के लिए भी उपलब्ध है.

System.load() का इस्तेमाल करके लोड की गई सभी नेटिव फ़ाइलों को, 'सिर्फ़ पढ़ने के लिए' के तौर पर मार्क किया जाना चाहिए. ऐसा न होने पर, सिस्टम UnsatisfiedLinkError दिखाता है.

हमारा सुझाव है कि ऐप्लिकेशन, डाइनैमिक तरीके से कोड लोड करने से बचें. ऐसा इसलिए, क्योंकि इससे ऐप्लिकेशन में कोड इंजेक्शन या कोड में छेड़छाड़ का खतरा काफ़ी बढ़ जाता है.

CP2 डेटा व्यू में व्यक्तिगत पहचान से जुड़ी जानकारी फ़ील्ड पर पाबंदी लगाना

Android 17 (एपीआई लेवल 37) और इसके बाद के वर्शन को टारगेट करने वाले ऐप्लिकेशन के लिए, संपर्क सूची 2 (CP2) डेटा व्यू से व्यक्तिगत पहचान से जुड़ी जानकारी (पीआईआई) वाले कुछ कॉलम को प्रतिबंधित करता है. इस बदलाव के लागू होने पर, उपयोगकर्ता की निजता को बेहतर बनाने के लिए, इन कॉलम को डेटा व्यू से हटा दिया जाता है. प्रतिबंधित कॉलम में ये शामिल हैं:

ContactsContract.Data से इन कॉलम का इस्तेमाल करने वाले ऐप्लिकेशन, इन्हें ContactsContract.RawContacts से निकाल सकते हैं. इसके लिए, उन्हें RAW_CONTACT_ID से जुड़ना होगा.

CP2 में एसक्यूएल की सख्त जांच लागू करें

Android 17 (एपीआई लेवल 37) और इसके बाद के वर्शन को टारगेट करने वाले ऐप्लिकेशन के लिए, Contacts Provider 2 (CP2) एसक्यूएल क्वेरी की पुष्टि सख्ती से करता है. ऐसा तब होता है, जब ContactsContract.Data टेबल को READ_CONTACTS अनुमति के बिना ऐक्सेस किया जाता है.

इस बदलाव के बाद, अगर किसी ऐप्लिकेशन के पास READ_CONTACTS की अनुमति नहीं है, तो ContactsContract.Data टेबल से क्वेरी करने पर, StrictColumns और StrictGrammar विकल्प सेट हो जाते हैं. अगर कोई क्वेरी ऐसे पैटर्न का इस्तेमाल करती है जो इनके साथ काम नहीं करता, तो उसे अस्वीकार कर दिया जाएगा और एक अपवाद दिखेगा.

इंटेलिजेंस

Android 17 में, सिस्टम इंटेलिजेंस से जुड़े ये बदलाव शामिल हैं.

setContentCaptureEnabled को बंद करना

कुछ डिवाइसों पर, कॉन्टेंट कैप्चर करने की सुविधा डिफ़ॉल्ट रूप से चालू होती है. इससे उपयोगकर्ता के डिवाइस पर मौजूद एआई की सुविधाएं, स्क्रीन पर मौजूद कॉन्टेंट का विश्लेषण कर पाती हैं. इससे आपको बेहतर अनुभव मिलता है.

Android 17 से, ContentCaptureManager.setContentCaptureEnabled(boolean) एपीआई का तरीका अब काम नहीं करता. Android 17 (एपीआई लेवल 37) या इसके बाद के वर्शन को टारगेट करने वाले ऐप्लिकेशन के लिए, setContentCaptureEnabled(false) को कॉल करने से कॉन्टेंट कैप्चर करने की सुविधा बंद नहीं होती.

अगर आपके ऐप्लिकेशन को कॉन्टेंट कैप्चर करने की सुविधा को बंद रखना है या सिस्टम को स्क्रीन का कॉन्टेंट कैप्चर करने से रोकना है, तो आपको FLAG_SECURE विंडो लेआउट पैरामीटर का इस्तेमाल करना होगा.

कॉन्टेंट कैप्चर करने की सुविधा बंद करने के लिए, अपनी विंडो पर FLAG_SECURE फ़्लैग सेट करें. इसका उदाहरण यहां दिया गया है:

Kotlin

window.setFlags(
    WindowManager.LayoutParams.FLAG_SECURE,
    WindowManager.LayoutParams.FLAG_SECURE
)

Java

getWindow().setFlags(
    WindowManager.LayoutParams.FLAG_SECURE,
    WindowManager.LayoutParams.FLAG_SECURE
);

ज़्यादा जानकारी के लिए, WindowManager.LayoutParams.FLAG_SECURE रेफ़रंस दस्तावेज़ देखें.

मीडिया

Android 17 में, मीडिया के काम करने के तरीके में ये बदलाव किए गए हैं.

बैकग्राउंड ऑडियो को बेहतर बनाना

Android 17 से, ऑडियो फ़्रेमवर्क बैकग्राउंड में ऑडियो इंटरैक्शन पर पाबंदियां लागू करता है. इनमें ऑडियो प्लेबैक, ऑडियो फ़ोकस के अनुरोध, और आवाज़ बदलने वाले एपीआई शामिल हैं. इससे यह पक्का किया जाता है कि ये बदलाव उपयोगकर्ता की अनुमति से ही शुरू किए गए हों.

ऑडियो से जुड़ी कुछ पाबंदियां सभी ऐप्लिकेशन पर लागू होती हैं. हालांकि, अगर कोई ऐप्लिकेशन Android 17 (एपीआई लेवल 37) को टारगेट करता है, तो पाबंदियां ज़्यादा सख्त होती हैं. अगर इनमें से कोई ऐप्लिकेशन बैकग्राउंड में ऑडियो के साथ इंटरैक्ट करता है, तो उसके लिए फ़ोरग्राउंड सेवा चालू होनी चाहिए. इसके अलावा, ऐप्लिकेशन को इनमें से एक या दोनों ज़रूरी शर्तें पूरी करनी होंगी:

  • फ़ोरग्राउंड सेवा में, इस्तेमाल के दौरान (डब्ल्यूआईयू) वाली सुविधाएं होनी चाहिए.
  • ऐप्लिकेशन के पास एग्ज़ैक्ट अलार्म की अनुमति होनी चाहिए. साथ ही, वह USAGE_ALARM ऑडियो स्ट्रीम के साथ इंटरैक्ट कर रहा हो.

जोखिम कम करने की रणनीतियों के साथ-साथ ज़्यादा जानकारी के लिए, बैकग्राउंड ऑडियो को बेहतर बनाना लेख पढ़ें.

डिवाइस के नाप या आकार

Android 17 में ये बदलाव किए गए हैं, ताकि अलग-अलग साइज़ और नाप या आकार वाले डिवाइसों पर उपयोगकर्ताओं को बेहतर अनुभव मिल सके.

बड़ी स्क्रीन (sw>=600dp) वाले डिवाइसों पर, ओरिएंटेशन, साइज़ बदलने, और आसपेक्ट रेशियो (लंबाई-चौड़ाई का अनुपात) से जुड़ी पाबंदियों को अनदेखा करने के लिए, प्लैटफ़ॉर्म एपीआई में बदलाव किए गए हैं

हमने Android 16 में प्लैटफ़ॉर्म एपीआई में बदलाव किए हैं. इनसे, टारगेट एपीआई लेवल 36 या इसके बाद के वर्शन को टारगेट करने वाले ऐप्लिकेशन के लिए, बड़ी स्क्रीन (sw >= 600dp) पर स्क्रीन की दिशा, साइज़ बदलने, और आसपेक्ट रेशियो (लंबाई-चौड़ाई का अनुपात) से जुड़ी पाबंदियों को अनदेखा किया जा सकेगा. डेवलपर के पास एसडीके 36 का इस्तेमाल करके, इन बदलावों से बाहर होने का विकल्प होता है. हालांकि, Android 17 (एपीआई लेवल 37) या इसके बाद के वर्शन को टारगेट करने वाले ऐप्लिकेशन के लिए, बाहर होने का यह विकल्प उपलब्ध नहीं होगा.

ज़्यादा जानकारी के लिए, ओरिएंटेशन और साइज़ बदलने से जुड़ी पाबंदियों को अनदेखा किया जाता है लेख पढ़ें.

कनेक्टिविटी

Android 17 में, ब्लूटूथ RFCOMM सॉकेट के लिए स्टैंडर्ड Java InputStream के व्यवहार के साथ अलाइन करने और एक जैसा अनुभव देने के लिए, यह बदलाव किया गया है.

RFCOMM के लिए, BluetoothSocket read() का एक जैसा व्यवहार

Android 17 (एपीआई लेवल 37) को टारगेट करने वाले ऐप्लिकेशन के लिए, RFCOMM पर आधारित BluetoothSocket से मिले InputStream का read() तरीका, सॉकेट बंद होने या कनेक्शन टूटने पर अब -1 दिखाता है.

इस बदलाव से, RFCOMM सॉकेट का व्यवहार LE CoC सॉकेट के जैसा हो जाता है. साथ ही, यह स्टैंडर्ड InputStream.read() दस्तावेज़ के मुताबिक हो जाता है. इसमें बताया गया है कि स्ट्रीम के खत्म होने पर, -1 दिखता है.

रीड लूप से बाहर निकलने के लिए, सिर्फ़ IOException को कैच करने पर निर्भर रहने वाले ऐप्लिकेशन पर इस बदलाव का असर पड़ सकता है. इसलिए, उन्हें ब्लूटूथ सॉकेट के रीड लूप को अपडेट करना चाहिए, ताकि -1 की रिटर्न वैल्यू की साफ़ तौर पर जांच की जा सके. इससे यह पक्का होता है कि रिमोट डिवाइस के डिसकनेक्ट होने या सॉकेट के बंद होने पर, लूप सही तरीके से खत्म हो जाए. सुझाए गए तरीके को लागू करने का उदाहरण देखने के लिए, ब्लूटूथ डेटा ट्रांसफ़र करें गाइड में मौजूद कोड स्निपेट देखें.