Service
ऐप्लिकेशन कॉम्पोनेंट, जो परफ़ॉर्म कर सकता है
बैकग्राउंड में लंबे समय से चल रही कार्रवाइयां. यह यूज़र इंटरफ़ेस उपलब्ध नहीं कराता. एक बार
शुरू हो, तो हो सकता है कि कोई सेवा कुछ समय तक चलती रहे, भले ही उपयोगकर्ता किसी अन्य सेवा पर स्विच करे
का इस्तेमाल करें. इसके अलावा, कोई कॉम्पोनेंट किसी सेवा के साथ इंटरैक्ट करने और परफ़ॉर्म करने के लिए बाइंड कर सकता है.
इंटरप्रोसेस कम्यूनिकेशन (आईपीसी). उदाहरण के लिए, कोई सेवा नेटवर्क से जुड़े लेन-देन को मैनेज कर सकती है,
संगीत इस्तेमाल करना, फ़ाइल I/O से परफ़ॉर्म करना या कॉन्टेंट देने वाले किसी व्यक्ति या कंपनी से इंटरैक्ट करना. ये सभी काम बैकग्राउंड में किए जा सकते हैं.
चेतावनी: कोई सेवा अपनी होस्टिंग के मुख्य थ्रेड में चलती है प्रोसेस; सेवा अपना थ्रेड नहीं बनाती है और न ही वह अपना थ्रेड बनाती है नहीं को किसी अलग प्रोसेस में चलाएं, जब तक कि आप कोई और निर्देश न दें. आपको ब्लॉक करने की कोई भी कार्रवाई चालू रखनी चाहिए ऐप्लिकेशन से बचने के लिए, सेवा में एक अलग थ्रेड काम नहीं कर रही (ANR) से जुड़ी गड़बड़ियां.
सेवाओं के टाइप
ये तीन अलग-अलग तरह की सेवाएं हैं:
- फ़ोरग्राउंड
-
फ़ोरग्राउंड सेवा की मदद से कुछ ऐसे काम किए जा रहे हैं जो उपयोगकर्ता. उदाहरण के लिए, कोई ऑडियो ऐप्लिकेशन किसी वीडियो को चलाने के लिए, फ़ोरग्राउंड सेवा का इस्तेमाल करता है ऑडियो ट्रैक. फ़ोरग्राउंड सेवाओं को एक सूचना दिखानी होगी. उपयोगकर्ता के इंटरैक्ट न करने के बावजूद, फ़ोरग्राउंड सेवाएं चलती रहती हैं ऐप के साथ.
फ़ोरग्राउंड सेवा का इस्तेमाल करते समय, आपको एक सूचना दिखानी होगी, ताकि उपयोगकर्ता सक्रिय रूप से जानते हैं कि सेवा चल रही है. इस सूचना से ये काम नहीं किए जा सकते को तब तक खारिज किया जाएगा, जब तक कि सेवा को रोका नहीं जाता या होता है.
कॉन्फ़िगर करने के तरीके के बारे में ज़्यादा जानें फ़ोरग्राउंड सेवाएं: है.
ध्यान दें: WorkManager एपीआई की मदद से, ज़रूरत के हिसाब से टास्क शेड्यूल किए जा सकते हैं. चल सकता है ज़रूरत पड़ने पर, इन जॉब को फ़ोरग्राउंड सेवाओं के तौर पर भी शामिल किया जा सकता है. कई मामलों में, WorkManager को सीधे फ़ोरग्राउंड सेवाओं का इस्तेमाल करना चाहिए.
- बैकग्राउंड
- बैकग्राउंड सेवा एक ऐसी कार्रवाई करती है जो सीधे तौर पर उसे नहीं दिखती
उपयोगकर्ता है. उदाहरण के लिए, अगर किसी ऐप्लिकेशन ने अपने स्टोरेज को कॉम्पैक्ट करने के लिए किसी सेवा का इस्तेमाल किया है,
जो आम तौर पर बैकग्राउंड में चलने वाली सेवा होती है.
ध्यान दें: अगर आपका ऐप्लिकेशन, एपीआई लेवल 26 या उसके बाद के लेवल को टारगेट करता है, तो सिस्टम, बैकग्राउंड में विज्ञापन चलाने पर पाबंदियां लागू करता है सेवाएं तब मुहैया कराएं, जब ऐप्लिकेशन खुद फ़ोरग्राउंड में न हो. ज़्यादातर उदाहरण के लिए, आपको किसी भी समय जगह की जानकारी ऐक्सेस करने के लिए, बैकग्राउंड. इसके बजाय, इसका इस्तेमाल करके टास्क शेड्यूल करें WorkManager.
- सीमित
- किसी सेवा को तब बाउंड किया जाता है, जब ऐप्लिकेशन का कोई कॉम्पोनेंट
bindService()
को कॉल करके उसे बाइंड करता है. सीमित सेवा, क्लाइंट-सर्वर की सुविधा देती है ऐसा इंटरफ़ेस जो कॉम्पोनेंट को सेवा के साथ इंटरैक्ट करने, अनुरोध भेजने, और नतीजे पाने की अनुमति देता है. साथ ही, इंटरप्रोसेस कम्यूनिकेशन (आईपीसी) के साथ भी ऐसा ही किया जा सकता है. सीमित सेवा सिर्फ़ चलती है जब तक कि कोई अन्य ऐप्लिकेशन घटक इसके साथ बाध्य न हो. कई कॉम्पोनेंट बाइंड किए जा सकते हैं लेकिन जब वे सभी अनबाइंड किए जाते हैं, तो सेवा खत्म हो जाती है.
हालांकि, इस दस्तावेज़ में आम तौर पर शुरू की गई और सीमित सेवाओं के बारे में अलग से चर्चा की गई है,
आपकी सेवा दोनों तरह से काम कर सकती है—इसे शुरू किया जा सकता है (अनिश्चित रूप से चलाने के लिए) और
बाइंडिंग. यहां सिर्फ़ यह निर्भर करता है कि आप दो कॉलबैक मेथड लागू करते हैं या नहीं: कॉम्पोनेंट को उसे शुरू करने की अनुमति देने के लिए onStartCommand()
और बाइंडिंग की अनुमति देने के लिए onBind()
.
भले ही आपकी सेवा प्रारंभ हो, सीमित हो या दोनों हो, ऐप्लिकेशन का कोई भी घटक
सेवा का इस्तेमाल (किसी अलग ऐप्लिकेशन से भी) उसी तरह कर सकता है जैसे कोई कॉम्पोनेंट इस्तेमाल कर सकता है
किसी गतिविधि—इसे Intent
से शुरू करके. हालांकि, आपके पास यह एलान करने का विकल्प भी है कि
को मेनिफ़ेस्ट फ़ाइल में निजी के रूप में सेव करना होगा और दूसरे ऐप्लिकेशन से इसके ऐक्सेस को ब्लॉक करना होगा.
इस बारे में ज़्यादा जानकारी, इस सेक्शन में सेवा की घोषणा के बारे में दी गई है
मेनिफ़ेस्ट.
सेवा और थ्रेड के बीच चुनना
सेवा सिर्फ़ एक कॉम्पोनेंट है, जो बैकग्राउंड में चल सकती है. भले ही, उपयोगकर्ता ऐसा न कर रहा हो आपके ऐप्लिकेशन के साथ इंटरैक्ट कर रहे हैं, इसलिए आपको कोई सेवा तभी बनानी चाहिए, जब आप ज़रूरत.
अगर आपको मुख्य थ्रेड के बाहर काम करना है, लेकिन ऐसा सिर्फ़ तब करना है, जब उपयोगकर्ता इंटरैक्ट कर रहा हो
अपने ऐप्लिकेशन के साथ काम करता है, तो आपको इसके बजाय किसी दूसरे ऐप्लिकेशन के संदर्भ में एक नया थ्रेड बनाना चाहिए
कॉम्पोनेंट. उदाहरण के लिए, अगर आपको गतिविधि के दौरान कोई संगीत चलाना है,
तो onCreate()
में थ्रेड बनाई जा सकती है,
इसे onStart()
में चलाना शुरू करें,
और onStop()
में इसे बंद कर दें.
साथ ही, java.util.concurrent
पैकेज में शामिल थ्रेड पूल और ईमेल एक्ज़ीक्यूट करने वाले टूल का इस्तेमाल करें
या ट्रेडिशनल के बजाय Kotlin कोरूटीन
Thread
क्लास. ज़्यादा जानकारी के लिए,
Android पर थ्रेडिंग दस्तावेज़, ताकि आपको इस बारे में ज़्यादा जानकारी मिल सके
एक्ज़ीक्यूशन को बैकग्राउंड थ्रेड पर ले जाने की सुविधा मिलती है.
याद रखें कि अगर आप किसी सेवा का उपयोग करते हैं, तो वह अब भी आपके ऐप्लिकेशन के मुख्य थ्रेड में डिफ़ॉल्ट है, इसलिए अगर यह सेवा में बहुत ज़्यादा काम करता है, तो आपको अब भी सेवा में एक नया थ्रेड बनाना चाहिए या कार्रवाइयों को ब्लॉक करने वाला टूल चुनें.
बुनियादी बातें
कोई सेवा बनाने के लिए, आपको Service
की एक सब-क्लास बनानी होगी या किसी सेवा का इस्तेमाल करना होगा
सब-क्लास का इस्तेमाल करके, इवेंट बनाए जा सकते हैं. लागू करने के दौरान, आपको कुछ कॉलबैक के तरीकों को बदलना होगा
यह सेवा के लाइफ़साइकल के अहम पहलुओं को मैनेज करता है. साथ ही, ऐसा तरीका उपलब्ध कराता है जिससे कॉम्पोनेंट
अगर उचित हो, तो सेवा से बाध्य करें. कॉलबैक के ये सबसे ज़रूरी तरीके हैं
ओवरराइड:
onStartCommand()
- जब कोई अन्य कॉम्पोनेंट (जैसे कि कोई गतिविधि) सेवा को चालू करने का अनुरोध करता है, तो सिस्टम इस तरीके को
startService()
कॉल करके शुरू करता है. इस तरीके के लागू होने पर, सेवा शुरू हो जाती है और बैकग्राउंड में भी बदलाव कर सकते हैं. अगर आप इसे लागू करते हैं, तोstopSelf()
याstopService()
पर कॉल करने पर यह काम पूरा हो जाएगा. अगर आपको सिर्फ़ बाइंडिंग उपलब्ध करानी है, तो आपको इस तरीके को लागू करने की ज़रूरत होती है. onBind()
- सिस्टम इस तरीके को
bindService()
को कॉल करके तब शुरू करता है, जब कोई दूसरा कॉम्पोनेंट सेवा से बाइंड (जैसे कि RPC) करना चाहता है. इस तरीके को लागू करते समय, आपको एक ऐसा इंटरफ़ेस उपलब्ध कराना होगा जो सेवा से संपर्क करने के लिएIBinder
का इस्तेमाल करें. आपको हमेशा इस तरीके को लागू करें; हालांकि, अगर आपको बाइंडिंग की अनुमति नहीं देनी है, तो शून्य. onCreate()
- सिस्टम इस तरीके को तब शुरू करता है, जब सेवा
पहले बनाया गया (इससे पहले कि यह किसी
onStartCommand()
याonBind()
). अगर सेवा पहले से चल रही है, तो यह तरीका कॉल किया गया. onDestroy()
- सिस्टम इस तरीके को तब इस्तेमाल करता है, जब सेवा का इस्तेमाल न किया जा रहा हो और उसे बंद किया जा रहा हो. रजिस्टर की गई थ्रेड जैसे सभी संसाधनों को हटाने के लिए, आपकी सेवा को इसे लागू करना चाहिए लिसनर या रिसीवर. यह सेवा को मिलने वाला आखिरी कॉल है.
अगर कोई कॉम्पोनेंट startService()
को कॉल करके सेवा शुरू करता है (जिसकी वजह से onStartCommand()
को कॉल किया जाता है), तो वह सेवा
तब तक चलता रहेगा जब तक कि यह stopSelf()
या किसी दूसरे के साथ खुद को बंद नहीं कर देता
कॉम्पोनेंट, stopService()
को कॉल करके इसे रोकता है.
अगर कोई कॉम्पोनेंट
सेवा बनाने के लिए bindService()
और onStartCommand()
को कॉल नहीं किया गया है, सेवा चालू है
सिर्फ़ तब तक, जब तक वह कॉम्पोनेंट इससे जुड़ा हो. सेवा के सभी क्लाइंट से अनबाउंड होने के बाद,
तब सिस्टम उसे नष्ट कर देता है.
Android सिस्टम किसी सेवा को सिर्फ़ तब बंद करता है, जब मेमोरी कम होती है और उसे सिस्टम को रिकवर करना होता है
जिसमें उपयोगकर्ता के फ़ोकस वाले गतिविधि के लिए संसाधन मौजूद होते हैं. अगर सेवा किसी ऐसी गतिविधि से बाध्य है जिसमें उपयोगकर्ता
तो उसके मरने की संभावना कम होती है; अगर सेवा को फ़ोरग्राउंड में चलने के लिए एलान किया जाता है, तो उसे शायद ही मारा जाता है.
अगर सेवा शुरू हो गई है और लंबे समय से चल रही है, तो सिस्टम इसकी पोज़िशन नीचे कर देता है
सूची में शामिल हैं, जो समय के साथ बैकग्राउंड में चलने वाले टास्क की सूची में शामिल हो जाती हैं. साथ ही, सेवा को नुकसान पहुंचने की आशंका ज़्यादा हो जाती है
किलिंग—अगर आपकी सेवा प्रारंभ हो गई है, तो आपको उसे इस तरह डिज़ाइन करना होगा कि वह रीस्टार्ट हो और
को ट्रैक करने की सुविधा मिलती है. अगर सिस्टम आपकी सेवा खत्म कर देता है, तो संसाधन बनते ही यह रीस्टार्ट हो जाता है
उपलब्ध है, लेकिन यह onStartCommand()
से मिलने वाली वैल्यू पर भी निर्भर करता है. Reader Revenue Manager को सेट अप करने के बारे में
जानें कि सिस्टम कब किसी सेवा को बंद कर सकता है. ज़्यादा जानकारी के लिए, प्रोसेस और थ्रेडिंग देखें
दस्तावेज़.
नीचे दिए गए सेक्शन में आपको पता चलेगा कि
startService()
और
bindService()
सेवा के तरीके और इस्तेमाल करने का तरीका
उन्हें ऐप्लिकेशन के दूसरे कॉम्पोनेंट से भी लिया जा सकता है.
मेनिफ़ेस्ट में किसी सेवा की जानकारी देना
आपको अपने ऐप्लिकेशन की सभी सेवाओं का एलान करना होगा मेनिफ़ेस्ट फ़ाइल की तरह ही, जैसे कि गतिविधियों और दूसरे कॉम्पोनेंट के लिए किया जाता है.
अपनी सेवा के बारे में बताने के लिए, <service>
एलिमेंट जोड़ें
<application>
के बच्चे के तौर पर
एलिमेंट. उदाहरण के लिए:
<manifest ... > ... <application ... > <service android:name=".ExampleService" /> ... </application> </manifest>
<service>
एलिमेंट देखें
का पालन करें.
<service>
एलिमेंट में कुछ और एट्रिब्यूट भी शामिल किए जा सकते हैं, ताकि
प्रॉपर्टी को परिभाषित करें, जैसे कि वे अनुमतियां जो सेवा और प्रोसेस को शुरू करने के लिए ज़रूरी हैं
तय करें कि सेवा किस तरह काम करती है. android:name
एट्रिब्यूट सिर्फ़ ज़रूरी एट्रिब्यूट है—यह सेवा के क्लास नाम के बारे में बताता है. इस तारीख के बाद
आप अपना ऐप्लिकेशन प्रकाशित करते हैं, तो ऐप्लिकेशन के टूट जाने के जोखिम से बचने के लिए इस नाम में कोई बदलाव न करें
ऐसा कोड जो सेवा को शुरू करने या उससे बाध्य करने के लिए साफ़ तौर पर इंटेंट पर निर्भर करता है (ब्लॉग पोस्ट पढ़ें,
इसे बदला नहीं जा सकता).
चेतावनी: यह पक्का करने के लिए कि आपका ऐप्लिकेशन सुरक्षित है, हमेशा
Service
को शुरू करने पर एक्सप्लिसिट इंटेंट और
आपकी सेवाएं लेता है. किसी सेवा को शुरू करने के लिए इंप्लिसिट इंटेंट का इस्तेमाल करना सुरक्षा के लिए खतरा है, क्योंकि आप ऐसा नहीं कर सकते
उस सेवा के बारे में पक्का करें जो इंटेंट के हिसाब से काम करती है. साथ ही, उपयोगकर्ता यह नहीं देख सकता कि वह सेवा कौनसी है
शुरू होता है. Android 5.0 (एपीआई लेवल 21) और इसके बाद के वर्शन में, कॉल करने पर सिस्टम एक अपवाद दिखाता है
इंप्लिसिट इंटेंट के साथ bindService()
.
ऐसा करके यह पक्का किया जा सकता है कि आपकी सेवा सिर्फ़ आपके ऐप्लिकेशन के लिए उपलब्ध हो. इसके लिए:
android:exported
सहित
एट्रिब्यूट जोड़ें और इसे false
पर सेट करें. यह अन्य ऐप्लिकेशन को आपकी
सेवा के लिए दोबारा इस्तेमाल किया जा सकता है.
ध्यान दें:
उपयोगकर्ता देख सकते हैं कि उनके डिवाइस पर कौनसी सेवाएं चल रही हैं. अगर उन्हें
अगर वे किसी सेवा को नहीं पहचानते हैं या उस पर भरोसा नहीं करते हैं, तो वे उस सेवा को बंद कर सकते हैं. तय सीमा में
उपयोगकर्ताओं को गलती से आपकी सेवा रोकनी न हो, इसके लिए आपको
इसे जोड़ने के लिए
android:description
एट्रिब्यूट को
<service>
एलिमेंट शामिल करने की ज़रूरत नहीं है. ब्यौरे में,
एक छोटा वाक्य दें जिसमें यह बताया गया हो कि यह सेवा क्या करती है और इसके क्या फ़ायदे हैं
यह उपलब्ध कराता है.
शुरू की गई सेवा बनाना
शुरू की गई सेवा वह सेवा होती है जिसे कोई दूसरा कॉम्पोनेंट startService()
को कॉल करके शुरू करता है. इससे सेवा को कॉल किया जाता है
onStartCommand()
तरीका.
जब कोई सेवा शुरू की जाती है, तो उसका एक लाइफ़साइकल होता है, जो
कॉम्पोनेंट बनाया गया है. सेवा बैकग्राउंड में लगातार चल सकती है, भले ही
जिस कॉम्पोनेंट ने इसे शुरू किया था वह खत्म हो गया है. इसलिए, काम करते समय सेवा अपने आप बंद हो जानी चाहिए
stopSelf()
को कॉल करने पर पूरा हो जाता है या कोई दूसरा कॉम्पोनेंट
stopService()
पर कॉल करके इसे रोकें.
गतिविधि जैसा कोई ऐप्लिकेशन कॉम्पोनेंट, startService()
को कॉल करके और Intent
पास करके सेवा शुरू कर सकता है
जो सेवा के बारे में बताता है. साथ ही, इसमें सेवा का इस्तेमाल करने के लिए पूरा डेटा शामिल होता है. सेवा को मिलने वाली सुविधाएं
इस Intent
को onStartCommand()
तरीके में.
उदाहरण के लिए, मान लें कि किसी गतिविधि के लिए किसी ऑनलाइन डेटाबेस में कुछ डेटा सेव करने की ज़रूरत है. गतिविधि
कोई कंपैनियन सेवा शुरू कर सकता है और startService()
को इंटेंट पास करके उसे बचाने के लिए डेटा डिलीवर कर सकता है. सेवा को onStartCommand()
में इंटेंट मिलता है, इंटरनेट से कनेक्ट होता है, और
डेटाबेस लेन-देन. लेन-देन पूरा होने पर, सेवा बंद हो जाती है और
नष्ट कर दिया गया.
चेतावनी: सेवा, ऐप्लिकेशन की प्रोसेस के हिसाब से ही काम करती है जिसमें उसे डिफ़ॉल्ट रूप से उस ऐप्लिकेशन के मुख्य थ्रेड में बनाया जाता है. अगर आपको जब उपयोगकर्ता उसी तो यह सेवा गतिविधि प्रदर्शन को धीमा कर देती है. ऐप्लिकेशन के इस्तेमाल पर असर डालने से बचने के लिए परफ़ॉर्मेंस के लिए, सेवा में नया थ्रेड शुरू करें.
Service
क्लास बेस होती है
क्लास का इस्तेमाल करें. जब आप इस क्लास को बढ़ाते हैं, तो एक नया थ्रेड बनाना ज़रूरी होता है जिसमें
सेवा अपने सभी काम पूरे कर सके; सेवा आपके ऐप्स के मुख्य थ्रेड का इसके द्वारा उपयोग करती है
डिफ़ॉल्ट बनाएं, जो आपके ऐप्लिकेशन की चल रही किसी भी गतिविधि के प्रदर्शन को धीमा कर सकती है.
Android फ़्रेमवर्क, IntentService
Service
की सब-क्लास है जो
वर्कर थ्रेड की सुविधा का इस्तेमाल करना होगा. इस क्लास का इस्तेमाल नहीं है
हम नए ऐप्लिकेशन के लिए इस्तेमाल करने का सुझाव देते हैं, क्योंकि Android 8 Oreo के साथ यह अच्छी तरह से काम नहीं करेगा. ऐसा इसलिए, क्योंकि
बैकग्राउंड में एक्ज़ीक्यूट करने की सीमाओं से जुड़ी जानकारी.
साथ ही, Android 11 और उसके बाद के वर्शन में, यह सुविधा काम नहीं करती.
आप jobIntentService का इस्तेमाल
को IntentService
से बदला जा सकता है. यह Android के नए वर्शन के साथ काम करता है.
इन सेक्शन में बताया गया है कि अपनी पसंद के मुताबिक बनाई गई सेवा को कैसे लागू किया जा सकता है. हालांकि, आपको इस्तेमाल के ज़्यादातर उदाहरणों के लिए, इसके बजाय WorkManager का इस्तेमाल करें. Android पर बैकग्राउंड प्रोसेसिंग की गाइड देखें और देखें कि क्या इसका कोई ऐसा समाधान है जो आपकी ज़रूरतों को पूरा करे.
सेवा क्लास को बढ़ाना
Service
क्लास को बढ़ाया जा सकता है
का इस्तेमाल करें. यहां बताया गया है कि बुनियादी तौर पर लागू करने का तरीका कैसा दिख सकता है:
Kotlin
class HelloService : Service() { private var serviceLooper: Looper? = null private var serviceHandler: ServiceHandler? = null // Handler that receives messages from the thread private inner class ServiceHandler(looper: Looper) : Handler(looper) { override fun handleMessage(msg: Message) { // Normally we would do some work here, like download a file. // For our sample, we just sleep for 5 seconds. try { Thread.sleep(5000) } catch (e: InterruptedException) { // Restore interrupt status. Thread.currentThread().interrupt() } // Stop the service using the startId, so that we don't stop // the service in the middle of handling another job stopSelf(msg.arg1) } } override fun onCreate() { // Start up the thread running the service. Note that we create a // separate thread because the service normally runs in the process's // main thread, which we don't want to block. We also make it // background priority so CPU-intensive work will not disrupt our UI. HandlerThread("ServiceStartArguments", Process.THREAD_PRIORITY_BACKGROUND).apply { start() // Get the HandlerThread's Looper and use it for our Handler serviceLooper = looper serviceHandler = ServiceHandler(looper) } } override fun onStartCommand(intent: Intent, flags: Int, startId: Int): Int { Toast.makeText(this, "service starting", Toast.LENGTH_SHORT).show() // For each start request, send a message to start a job and deliver the // start ID so we know which request we're stopping when we finish the job serviceHandler?.obtainMessage()?.also { msg -> msg.arg1 = startId serviceHandler?.sendMessage(msg) } // If we get killed, after returning from here, restart return START_STICKY } override fun onBind(intent: Intent): IBinder? { // We don't provide binding, so return null return null } override fun onDestroy() { Toast.makeText(this, "service done", Toast.LENGTH_SHORT).show() } }
Java
public class HelloService extends Service { private Looper serviceLooper; private ServiceHandler serviceHandler; // Handler that receives messages from the thread private final class ServiceHandler extends Handler { public ServiceHandler(Looper looper) { super(looper); } @Override public void handleMessage(Message msg) { // Normally we would do some work here, like download a file. // For our sample, we just sleep for 5 seconds. try { Thread.sleep(5000); } catch (InterruptedException e) { // Restore interrupt status. Thread.currentThread().interrupt(); } // Stop the service using the startId, so that we don't stop // the service in the middle of handling another job stopSelf(msg.arg1); } } @Override public void onCreate() { // Start up the thread running the service. Note that we create a // separate thread because the service normally runs in the process's // main thread, which we don't want to block. We also make it // background priority so CPU-intensive work doesn't disrupt our UI. HandlerThread thread = new HandlerThread("ServiceStartArguments", Process.THREAD_PRIORITY_BACKGROUND); thread.start(); // Get the HandlerThread's Looper and use it for our Handler serviceLooper = thread.getLooper(); serviceHandler = new ServiceHandler(serviceLooper); } @Override public int onStartCommand(Intent intent, int flags, int startId) { Toast.makeText(this, "service starting", Toast.LENGTH_SHORT).show(); // For each start request, send a message to start a job and deliver the // start ID so we know which request we're stopping when we finish the job Message msg = serviceHandler.obtainMessage(); msg.arg1 = startId; serviceHandler.sendMessage(msg); // If we get killed, after returning from here, restart return START_STICKY; } @Override public IBinder onBind(Intent intent) { // We don't provide binding, so return null return null; } @Override public void onDestroy() { Toast.makeText(this, "service done", Toast.LENGTH_SHORT).show(); } }
उदाहरण के लिए दिया गया कोड, onStartCommand()
में आने वाले सभी कॉल को हैंडल करता है
और काम को बैकग्राउंड थ्रेड पर चलने वाले Handler
पर पोस्ट कर देता है. यह बिलकुल IntentService
की तरह काम करता है और सभी अनुरोधों को क्रम से, एक के बाद एक प्रोसेस करता है.
थ्रेड पूल पर काम चलाने के लिए, कोड में बदलाव किया जा सकता है. उदाहरण के लिए, अगर आपको एक साथ कई अनुरोध चलाने हैं.
ध्यान दें कि onStartCommand()
तरीके से
पूर्णांक. पूर्णांक वह वैल्यू है जिससे यह पता चलता है कि सिस्टम को
किसी इवेंट को खत्म कर देता है. रिटर्न वैल्यू
onStartCommand()
से शुरू, इनमें से एक होना चाहिए
कॉन्सटेंट:
START_NOT_STICKY
- अगर सिस्टम
onStartCommand()
के वापस लौटने के बाद सेवा को खत्म कर देता है, तो जब तक कोई कार्रवाई बाकी नहीं है, तब तक सेवा को फिर से न बनाएं डिलीवर करने का इरादा है. यह सबसे सुरक्षित विकल्प है, ताकि ज़रूरत न होने पर सेवा का इस्तेमाल न किया जा सके और जब आपका ऐप्लिकेशन किसी अधूरे काम को आसानी से फिर से शुरू कर सके. START_STICKY
- अगर सिस्टम
onStartCommand()
के वापस आने के बाद सेवा को बंद कर देता है, तो सेवा को फिर से बनाएं औरonStartCommand()
को कॉल करें, लेकिन पिछले इंटेंट को फिर से डिलीवर न करें. इसके बजाय, सिस्टमonStartCommand()
को अमान्य इंटेंट, जब तक सेवा शुरू करने के लिए लंबित इंटेंट न हों. ऐसी स्थिति में, वे इंटेंट डिलीवर कर दिए जाते हैं. यह उन मीडिया प्लेयर (या मिलती-जुलती सेवाओं) के लिए सही है जो निर्देशों को एक्ज़ीक्यूट कर रहा है, लेकिन अनिश्चित काल तक चल रहा है और काम का इंतज़ार कर रहा है. START_REDELIVER_INTENT
- अगर सिस्टम
onStartCommand()
के वापस लौटने के बाद सेवा को खत्म कर देता है, तो सेवा को फिर से बनाएं औरonStartCommand()
को उस अंतिम इंटेंट के साथ कॉल करें जिसे डिलीवर किया गया था सेवा. कोई भी बकाया इंटेंट, बदले में डिलीवर किया जाता है. यह उन सेवाओं के लिए सही है जो कोई ऐसा काम कर रहा हो जिसे तुरंत फिर से शुरू किया जाना चाहिए. जैसे, कोई फ़ाइल डाउनलोड करना.
रिटर्न वैल्यू के बारे में ज़्यादा जानकारी के लिए, लिंक की गई रेफ़रंस फ़ाइल देखें दस्तावेज़ के तौर पर इस्तेमाल किया जा सकता है.
सेवा शुरू करना
किसी ऐक्टिविटी या ऐप्लिकेशन के अन्य कॉम्पोनेंट से कोई सेवा शुरू करने के लिए, ये काम किए जा सकते हैं:
Intent
पास कर रहा है
startService()
या startForegroundService()
तक. कॉन्टेंट बनाने
Android सिस्टम, सेवा के onStartCommand()
तरीके को कॉल करता है और उसे Intent
पास करता है,
जो बताता है कि कौनसी सेवा शुरू करनी है.
ध्यान दें: अगर आपका ऐप्लिकेशन, एपीआई लेवल 26 या उसके बाद के वर्शन को टारगेट करता है, तो सिस्टम
बैकग्राउंड में चलने वाली सेवाएं इस्तेमाल करने या बनाने पर पाबंदी लगाती है, बशर्ते ऐप्लिकेशन
खुद फ़ोरग्राउंड में हो. अगर किसी ऐप्लिकेशन को फ़ोरग्राउंड सेवा बनाने की ज़रूरत है,
ऐप्लिकेशन को startForegroundService()
पर कॉल करना चाहिए. इस तरीके से एक बैकग्राउंड सेवा बनती है, लेकिन
प्रणाली को इस बात का संकेत देता है कि सेवा अपना प्रचार
होता है. सेवा बन जाने के बाद, सेवा को
इसमें startForeground()
तरीका चुना गया
पाँच सेकंड.
उदाहरण के लिए, किसी गतिविधि के लिए startService()
के साथ एक्सप्लिसिट इंटेंट का इस्तेमाल करके, पिछले सेक्शन (HelloService
) में उदाहरण सेवा शुरू की जा सकती है, जैसा कि यहां दिखाया गया है:
Kotlin
startService(Intent(this, HelloService::class.java))
Java
startService(new Intent(this, HelloService.class));
startService()
तरीका तुरंत वापस आ जाता है, और
Android सिस्टम, सेवा की onStartCommand()
तरीके को कॉल करता है. अगर सेवा पहले से चालू नहीं है, तो सिस्टम पहले onCreate()
को कॉल करता है. इसके बाद, यह कॉल करता है
onStartCommand()
.
अगर सेवा बाइंडिंग भी उपलब्ध नहीं कराती, तो startService()
के साथ डिलीवर किया गया इंटेंट,
ऐप्लिकेशन के कॉम्पोनेंट और सेवा के बारे में बताया गया है. हालांकि, अगर आपको सेवा से कोई नतीजा वापस भेजना है, तो
सेवा शुरू करने वाला क्लाइंट, ब्रॉडकास्ट के लिए PendingIntent
बना सकता है
(getBroadcast()
के साथ) और इसे सेवा पर डिलीवर करें
Intent
में, जो सेवा शुरू करता है. इसके बाद, सेवा देने वाली कंपनी
ब्रॉडकास्ट करें, ताकि नतीजा डिलीवर किया जा सके.
सेवा शुरू करने के लिए कई अनुरोध मिलने पर, सेवा के उपयोगकर्ताओं को कई बार कॉल किए जाते हैं
onStartCommand()
. हालांकि, रोकने के लिए सिर्फ़ एक अनुरोध
सेवा (stopSelf()
या stopService()
वाली) को रोकना ज़रूरी है.
सेवा को रोकना
शुरू की गई सेवा को अपना लाइफ़साइकल खुद मैनेज करना होगा. इसका मतलब है कि सिस्टम या
सेवा को तब तक नष्ट करना, जब तक इसे सिस्टम मेमोरी और सेवा को रिकवर न करना पड़े
onStartCommand()
के वापस लौटने के बाद चलना जारी रहेगा. कॉन्टेंट बनाने
stopSelf()
या अन्य को कॉल करने पर सेवा अपने-आप बंद हो जानी चाहिए
कॉम्पोनेंट, stopService()
पर कॉल करके इसे बंद कर सकता है.
stopSelf()
या stopService()
पर बंद करने का अनुरोध करने पर, सिस्टम उसे तुरंत बंद कर देता है
किया जा सकता है.
अगर आपकी सेवा onStartCommand()
के लिए एक साथ कई अनुरोध हैंडल करती है, तो आपको
सेवा शुरू करने के बाद, जब आप शुरुआती अनुरोध को प्रोसेस कर लें, क्योंकि हो सकता है कि आपको कोई नया
(पहले अनुरोध के आखिर में रोकने से दूसरा अनुरोध खत्म हो जाता है). इससे बचने के लिए
इस समस्या को हल करने के लिए, आप stopSelf(int)
का इस्तेमाल करके यह पक्का कर सकते हैं कि
सेवा हमेशा सबसे हाल ही के प्रारंभ अनुरोध पर आधारित होती है. इसका मतलब है कि stopSelf(int)
को कॉल करने पर, आपने शुरुआती अनुरोध का आईडी (startId
) पास कर दिया है
onStartCommand()
पर डिलीवर किया गया) जिस पर रोक लगाने का आपका अनुरोध है
से मेल खाती हो. इसके बाद, अगर stopSelf(int)
को कॉल करने से पहले, सेवा को शुरू करने का नया अनुरोध मिलता है, तो आईडी मैच नहीं होगा और सेवा बंद नहीं होगी.
चेतावनी: सिस्टम के संसाधनों को बर्बाद होने और इनके इस्तेमाल से बचने के लिए
बैटरी पावर, पक्का करें कि काम पूरा हो जाने पर आपका ऐप्लिकेशन अपनी सेवाएं रोक दे.
अगर ज़रूरी हो, तो अन्य कॉम्पोनेंट stopService()
पर कॉल करके सेवा को रोक सकते हैं. भले ही, आपने सेवा के लिए बाइंडिंग चालू की हो,
अगर कभी भी onStartCommand()
पर कॉल आता है, तो आपको इस सेवा को खुद बंद करना होगा.
किसी सेवा के लाइफ़साइकल के बारे में ज़्यादा जानने के लिए, सेवा की लाइफ़साइकल मैनेज करना के बारे में नीचे दिया गया सेक्शन देखें.
सीमित सेवा बनाना
बाउंड सेवा वह होती है जो ऐप्लिकेशन के कॉम्पोनेंट को, bindService()
को कॉल करके बाइंड करने की अनुमति देती है. इससे, एक लंबे समय तक चलने वाला कनेक्शन बन जाता है.
आम तौर पर, यह कॉम्पोनेंट को startService()
को कॉल करके इसे शुरू करने की अनुमति नहीं देता है.
अगर आपको गतिविधियों से सेवा का इस्तेमाल करना है, तो सीमित सेवा बनाएं और अपने ऐप्लिकेशन के दूसरे घटकों से या अपने ऐप्लिकेशन के कुछ फ़ंक्शन को इंटरप्रोसेस कम्यूनिकेशन (आईपीसी) के ज़रिए दूसरे ऐप्लिकेशन इस्तेमाल करना शामिल है.
सीमित सेवा बनाने के लिए, onBind()
कॉलबैक तरीका लागू करें, ताकि IBinder
को दिखाया जा सके
सेवा के साथ संचार के लिए इंटरफ़ेस तय करता है. इसके बाद, ऐप्लिकेशन के अन्य कॉम्पोनेंट कॉल कर सकते हैं
इंटरफ़ेस को फिर से पाने के लिए bindService()
और
सेवा पर कॉल करने के तरीके शुरू करें. यह सेवा सिर्फ़ ऐप्लिकेशन के कॉम्पोनेंट को सेवा देती है
इस पर लागू होता है, इसलिए जब सेवा से जुड़ा कोई कॉम्पोनेंट नहीं होता है, तो सिस्टम इसे खत्म कर देता है.
आपको किसी बाध्य सेवा को उसी तरह बंद करने की ज़रूरत नहीं है जिस तरह से आपको सेवा
onStartCommand()
तक शुरू हुआ.
सीमित सेवा बनाने के लिए, आपको ऐसा इंटरफ़ेस तय करना होगा जो यह बताए कि क्लाइंट
हमारी सेवा से संपर्क करें. सेवा के बीच में यह इंटरफ़ेस
और यह ज़रूरी है कि क्लाइंट, IBinder
को लागू करता हो. साथ ही, यह ज़रूरी है कि आपकी सेवा
onBind()
कॉलबैक मेथड से वापस करें. क्लाइंट को IBinder
मिलने के बाद, ये प्रोसेस शुरू हो सकती हैं
उस इंटरफ़ेस की मदद से सेवा के साथ इंटरैक्ट करते हैं.
एक ही समय पर एक से ज़्यादा क्लाइंट, सेवा का इस्तेमाल कर सकते हैं. जब कोई क्लाइंट
तो यह unbindService()
को हटाने के लिए कॉल करता है.
जब कोई क्लाइंट सेवा से बाध्य नहीं होता है, तो सिस्टम सेवा को खत्म कर देता है.
सीमित सेवा को लागू करने के कई तरीके हैं. साथ ही, लागू करने का तरीका ज़्यादा है यह अभी शुरू की गई सेवा से भी ज़्यादा मुश्किल है. इन वजहों से, सेवाओं को सीमित तौर पर इस्तेमाल करने से जुड़ी चर्चा बाउंड सेवाओं के बारे में अलग दस्तावेज़ होना चाहिए.
उपयोगकर्ता को सूचनाएं भेजी जा रही हैं
जब कोई सेवा चालू हो, तो वह स्नैकबार से जुड़ी सूचनाओं या स्टेटस बार से जुड़ी सूचनाओं का इस्तेमाल करके, उपयोगकर्ता को इवेंट की सूचना दे सकती है.
स्नैकबार सूचना एक ऐसा मैसेज है जो मौजूदा विंडो की सतह पर सिर्फ़ तय करें. स्टेटस बार में मिलने वाली सूचना के साथ, स्टेटस बार में एक आइकॉन दिखता है. ऐसा करें. इस मैसेज को उपयोगकर्ता कोई कार्रवाई करने के लिए चुन सकता है. जैसे, कोई गतिविधि शुरू करना.
आम तौर पर, बैकग्राउंड में काम करते समय जैसे कि स्टेटस बार सूचना का इस्तेमाल करना सबसे अच्छी तकनीक है फ़ाइल का डाउनलोड पूरा हो गया है और उपयोगकर्ता अब उस पर कार्रवाई कर सकता है. जब उपयोगकर्ता बड़े किए गए व्यू से सूचना चुनता है. सूचना से कोई गतिविधि शुरू हो सकती है (जैसे, डाउनलोड की गई फ़ाइल दिखाना).
किसी सेवा की लाइफ़साइकल मैनेज करना
किसी गतिविधि की तुलना में, किसी सेवा की लाइफ़साइकल काफ़ी आसान होती है. हालांकि, यह और भी ज़्यादा के लिए, इस बात पर बारीकी से ध्यान देना ज़रूरी है कि आपकी सेवा कैसे बनाई और खत्म की गई है, क्योंकि सेवा को उपयोगकर्ता की जानकारी के बिना बैकग्राउंड में चलाया जा सकता है.
सेवा की लाइफ़साइकल उसके हिसाब से बनाई जा सकती है, जैसे कि इसे बनाए जाने से लेकर, बंद किए जाने तक इन दो पाथ में से कोई एक:
- शुरू की गई सेवा
यह सेवा तब बनाई जाती है, जब किसी दूसरे कॉम्पोनेंट ने
startService()
को कॉल किया हो. फिर सेवा अनिश्चित समय तक चलती रहती है और आवश्यक है किstopSelf()
को कॉल करके खुद को रोक सकता है. दूसरा कॉम्पोनेंट भीstopService()
पर कॉल करके सेवा पाएं. सेवा बंद होने पर, सिस्टम उसे बंद कर देता है. - सीमित सेवा
यह सेवा तब शुरू की जाती है, जब कोई दूसरा कॉम्पोनेंट (क्लाइंट)
bindService()
को कॉल करता है. इसके बाद, क्लाइंट सेवा से संपर्क करता हैIBinder
इंटरफ़ेस के ज़रिए ऐसा किया जा सकता है. क्लाइंट कॉल करके कनेक्शन बंद कर सकता हैunbindService()
. कई क्लाइंट इनसे बाइंड कर सकते हैं उसी सेवा को नष्ट कर देता है और जब वे सभी बंद हो जाते हैं, तो सिस्टम सेवा को नष्ट कर देता है. सेवा खुद को रोकने की ज़रूरत नहीं है.
ये दोनों पाथ पूरी तरह से अलग नहीं हैं. आपके पास पहले से मौजूद किसी सेवा से जुड़ने का विकल्प है
startService()
से शुरू हुआ. उदाहरण के लिए, आपके पास
बैकग्राउंड संगीत सेवा शुरू करने के लिए, startService()
को Intent
पर कॉल करें. इससे आपको संगीत चलाने के लिए पहचान मिलेगी. बाद में,
हो सकता है कि जब उपयोगकर्ता, प्लेयर पर कुछ कंट्रोल करना चाहता हो या
मौजूदा गाने का इस्तेमाल करने के दौरान, bindService()
पर कॉल करके कोई गतिविधि इस सेवा से जुड़ी हो सकती है. ऐसे मामलों में, stopService()
या stopSelf()
तब तक सेवा को बंद नहीं करता, जब तक कि सभी क्लाइंट इसकी सेवाएं लेना बंद नहीं कर देते.
लाइफ़साइकल कॉलबैक लागू करना
किसी गतिविधि की तरह, किसी सेवा में भी लाइफ़साइकल कॉलबैक के तरीके होते हैं. इन तरीकों को मॉनिटर करने के लिए लागू किया जा सकता है सेवा की स्थिति में बदलाव करता है और सही समय पर काम करता है. नीचे दिया गया स्केलेटन सेवा में, लाइफ़साइकल के हर तरीके को दिखाया जाता है:
Kotlin
class ExampleService : Service() { private var startMode: Int = 0 // indicates how to behave if the service is killed private var binder: IBinder? = null // interface for clients that bind private var allowRebind: Boolean = false // indicates whether onRebind should be used override funonCreate
() { // The service is being created } override funonStartCommand
(intent: Intent?, flags: Int, startId: Int): Int { // The service is starting, due to a call to startService() return startMode } override funonBind
(intent: Intent): IBinder? { // A client is binding to the service with bindService() return binder } override funonUnbind
(intent: Intent): Boolean { // All clients have unbound with unbindService() return allowRebind } override funonRebind
(intent: Intent) { // A client is binding to the service with bindService(), // after onUnbind() has already been called } override funonDestroy
() { // The service is no longer used and is being destroyed } }
Java
public class ExampleService extends Service { int startMode; // indicates how to behave if the service is killed IBinder binder; // interface for clients that bind boolean allowRebind; // indicates whether onRebind should be used @Override public voidonCreate
() { // The service is being created } @Override public intonStartCommand
(Intent intent, int flags, int startId) { // The service is starting, due to a call tostartService()
return startMode; } @Override public IBinderonBind
(Intent intent) { // A client is binding to the service withbindService()
return binder; } @Override public booleanonUnbind
(Intent intent) { // All clients have unbound withunbindService()
return allowRebind; } @Override public voidonRebind
(Intent intent) { // A client is binding to the service withbindService()
, // after onUnbind() has already been called } @Override public voidonDestroy
() { // The service is no longer used and is being destroyed } }
ध्यान दें: गतिविधि के लाइफ़साइकल कॉलबैक के तरीकों से अलग, इन कॉलबैक के तरीकों के सुपरक्लास को लागू करने के लिए, कॉल करने की ज़रूरत नहीं है.
दूसरी इमेज में किसी सेवा के लिए, आम तौर पर इस्तेमाल किए जाने वाले कॉलबैक के तरीके दिखाए गए हैं. हालांकि, यह इमेज अलग-अलग हो सकती है
उन सेवाओं से जिन्हें startService()
ने बनाया है
इसे bindService()
ने बनाया है. इसे जारी रखें
ध्यान रखें कि कोई भी सेवा, चाहे उसे किसी भी तरह से शुरू किया गया हो, संभावित तौर पर क्लाइंट को उसका पालन करने की अनुमति मिल सकती है.
एक सेवा जिसे शुरुआत में onStartCommand()
के साथ शुरू किया गया था (क्लाइंट ने startService()
को कॉल किया था)
इसके बाद भी onBind()
पर कॉल आ सकता है (जब कोई क्लाइंट कॉल करेगा
bindService()
).
इन तरीकों को लागू करके, सेवा के इन दो नेस्ट किए गए लूपों पर नज़र रखी जा सकती है लाइफ़साइकल:
- किसी सेवा का पूरा लाइफ़टाइम,
onCreate()
को कॉल करने औरonDestroy()
के वापस आने के समय के बीच होता है. किसी गतिविधि की तरह, सेवा अपना शुरुआती सेट अपonCreate()
औरonDestroy()
में बाकी सभी संसाधन रिलीज़ करता है. उदाहरण के लिए, संगीत प्लेबैक सेवा, वह थ्रेड बना सकती है जहांonCreate()
में संगीत चलाया जाता है. इसके बाद, वहonDestroy()
में उस थ्रेड को बंद कर सकती है.ध्यान दें:
onCreate()
औरonDestroy()
तरीकों को सभी सेवाओं के लिए कॉल किया जाता है, चाहे इन्हेंstartService()
याbindService()
ने बनाया है. - किसी सेवा की चालू रहने की अवधि,
onStartCommand()
याonBind()
पर किए गए कॉल से शुरू होती है. हर तरीकाIntent
दिया जाता है, जिसेstartService()
याbindService()
को पास किया जाता है.अगर सेवा शुरू कर दी गई है, तो लाइफ़टाइम गतिविधि उसी समय खत्म हो जाती है जिस समय यह सेवा पूरी ज़िंदगी में इस्तेमाल की जाती थी खत्म हो जाएगा (
onStartCommand()
के लौटाने के बाद भी सेवा चालू रहेगी). अगर सेवा बाउंड है, तोonUnbind()
के लौटने पर, ऐक्टिव लाइफ़टाइम खत्म हो जाता है.
ध्यान दें: हालांकि एक शुरू की गई सेवा को
या तो stopSelf()
या stopService()
,
सेवा (onStop()
कॉलबैक की सुविधा नहीं है). जब तक सेवा क्लाइंट तक सीमित न हो,
सेवा बंद होने पर, सिस्टम इसे बंद कर देता है—सिर्फ़ onDestroy()
ही कॉलबैक होता है.
बाइंडिंग उपलब्ध कराने वाली सेवा बनाने के बारे में ज़्यादा जानकारी के लिए, बाउंड सेवाएं दस्तावेज़ देखें,
इसमें onRebind()
के बारे में ज़्यादा जानकारी
कॉलबैक मेथड का इस्तेमाल, की लाइफ़साइकल मैनेज करने के बारे में बताया गया है
सीमित सेवा.