runBlocking — यह क्या है, ब्लॉकिंग ब्रिज और यह कैसे काम करता है

लेखक: IT Sectr प्रकाशित: 2026-06-22 पढ़ने का समय: 7 मिनट

runBlocking — Kotlin में एक Coroutine Builder जो पास्ड कोरूटीन के पूर्ण होने तक वर्तमान थ्रेड को ब्लॉक करता है। launch और async के विपरीत, यह suspend फ़ंक्शन नहीं है और सामान्य (blocking) कोड से बुलाया जा सकता है। JetBrains प्रदान, 2024 के अनुसार, runBlocking सिंक्रोनस और असिंक्रोनस दुनियाओं के बीच एक पुल के रूप में कार्य करता है, जो main फ़ंक्शन और परीक्षणों से कोरूटीन शुरू करने की अनुमति देता है।

मुख्य बातें

  • runBlocking — एक ब्लॉकिंग बिल्डर जो CoroutineScope बनाता है और कोरूटीन के पूर्ण होने का इंतजार करता है
  • थ्रेड ब्लॉकिंग — runBlocking वर्तमान थ्रेड को कोरूटीन और उसके सभी चाइल्ड के पूर्ण होने तक रोके रखता है
  • प्रवेश बिंदु — main(), JUnit परीक्षण और blocking और async कोड के बीच पुल
  • Android के Main थ्रेड पर निषिद्ध — UI थ्रेड पर runBlocking कॉल करने से ANR होता है
  • विकल्प — Android के लिए lifecycleScope, viewModelScope, TestCoroutineDispatcher

runBlocking क्या है?

runBlocking एक Kotlin फ़ंक्शन है जो एक नया CoroutineScope बनाता है और पास्ड कोरूटीन को शुरू करता है, वर्तमान थ्रेड को तब तक ब्लॉक करता है जब तक वह पूर्णतः पूरा नहीं हो जाता। अन्य सभी Coroutine Builder के विपरीत, runBlocking एक suspend फ़ंक्शन नहीं है और सामान्य सिंक्रोनस कोड से बुलाया जा सकता है। runBlocking का हस्ताक्षर CoroutineContext और एक suspend ब्लॉक लेता है, जो T प्रकार का परिणाम लौटाता है।

kotlin
public fun <T> runBlocking(
    context: CoroutineContext = EmptyCoroutineContext,
    block: suspend CoroutineScope.() -> T
): T

runBlocking वर्तमान थ्रेड पर एक नया event-loop शुरू करता है। जब कोरूटीन एक suspend फ़ंक्शन (जैसे delay() या await()) को कॉल करता है, runBlocking थ्रेड को ब्लॉक करता है और निलंबित कोरूटीन के फिर से शुरू होने तक उसी थ्रेड पर अन्य निर्धारित कोरूटीन को निष्पादित करता है। यह सहकारी ब्लॉकिंग है — थ्रेड निष्क्रिय नहीं होता बल्कि अन्य कोरूटीन को प्रोसेस करता है।

runBlocking कैसे काम करता है

runBlocking का आंतरिक तंत्र event-loop पर आधारित है: जब कोई suspend फ़ंक्शन कॉल किया जाता है, runBlocking वर्तमान ब्लॉक के निष्पादन को रोक देता है और क्यू से अन्य कोरूटीन चलाता है। जब suspend फ़ंक्शन पूरा होता है, निष्पादन फिर से शुरू होता है। यह चक्र तब तक जारी रहता है जब तक सभी कोरूटीन समाप्त नहीं हो जातीं।

Event-loop के अंदर

runBlocking कोरूटीन के निष्पादन के लिए अपना स्वयं का एकल-थ्रेड पूल उपयोग करता है। Dispatchers.IO या Default के विपरीत, runBlocking थ्रेड नहीं बदलता — यह सभी कोरूटीन को वर्तमान थ्रेड पर संचालित करता है, उनके निष्पादन को इंटरलेव करता है। यह एकमात्र बिल्डर है जो उसी थ्रेड पर निष्पादन की गारंटी देता है।

kotlin
fun main() {
    val threadName = Thread.currentThread().getName()
    println("runBlocking से पहले $threadName पर")

    val result = runBlocking {
        println("runBlocking के अंदर ${Thread.currentThread().getName()} पर")
        delay(500L)
        "Done"
    }

    println("runBlocking के बाद: $result")
}

आउटपुट दिखाएगा कि तीनों println कथन एक ही थ्रेड पर निष्पादित होते हैं। runBlocking थ्रेड नहीं बदलता बल्कि event-loop का उपयोग करके एक ही थ्रेड के अंदर सहकारी मल्टिटास्किंग को व्यवस्थित करता है।

runBlocking कब उपयोग करें

runBlocking तीन परिदृश्यों में उचित है: कंसोल एप्लिकेशन में main() प्रवेश बिंदु, suspend फ़ंक्शन के यूनिट परीक्षण और पुल — callback-आधारित या blocking लाइब्रेरियों से suspend कोड कॉल करना। प्रोडक्शन Android कोड में, मुख्य थ्रेड पर इसका उपयोग सदर निषिद्ध है।

परिदृश्यउपयोग्यताजोखिम
main() कंसोल एप्लिकेशन काहाँकोई नहीं — यह प्रवेश बिंदु है, थ्रेड UI को ब्लॉक नहीं करता
JUnit परीक्षणहाँन्यूनतम — परीक्षण परिभाषा के अनुसार सिंक्रोनस होते हैं
Android UI थ्रेडनहींANR, लैग, इंटरफ़ेस फ्रीज़
Callback → Coroutineहाँ, सावधानी सेलंबे ऑपरेशनों में थ्रेड पूल ब्लॉकिंग

Android परीक्षणों के लिए, runBlocking के बजाय kotlinx-coroutines-test का TestDispatcher के साथ उपयोग करें। यह समय नियंत्रण, स्वचालित सफाई और परीक्षण पृथक्करण प्रदान करता है।

runBlocking के विकल्प

अधिकांश परिदृश्यों में, runBlocking को असिंक्रोनस विकल्पों से बदला जा सकता है और बदलना चाहिए। Android के लिए, ये viewModelScope, lifecycleScope या उपयुक्त डिस्पैचर के साथ CoroutineScope हैं। परीक्षणों के लिए — TestCoroutineDispatcher और runTest।

kotlin
    // बुरा: Android मुख्य थ्रेड पर runBlocking
runBlocking(Dispatchers.Main) {
    val result = networkApi.fetchData()
    textView.setText(result)
}

// अच्छा: lifecycleScope
lifecycleScope.launch {
    val result = withContext(Dispatchers.IO) { networkApi.fetchData() }
    textView.setText(result)
}

परीक्षणों के लिए, बदलाव runTest है kotlinx-coroutines-test से। यह वास्तविक प्रतीक्षा के बिना विलंब का परीक्षण करने की अनुमति देने के लिए आभासी समय के साथ TestCoroutineScope बनाता है। यह परीक्षणों को तेज करता है और उन्हें निर्धार्यिक बनाता है।

runBlocking उपयोग उदाहरण

सबसे सामान्य परिदृश्य suspend फ़ंक्शन का परीक्षण करना है। परीक्षणों में runBlocking आपको आर्किटेक्चर को बदले बिना एक कोरूटीन परिणाम की प्रतीक्षा करने की अनुमति देता है। दूसरा परिदृश्य callback API वाली लाइब्रेरियाँ हैं, जहाँ suspend फ़ंक्शन runBlocking के माध्यम से blocking संदर्भ से बुलाए जाते हैं।

kotlin
// runBlocking के साथ suspend फ़ंक्शन का परीक्षण
class RepositoryTest {
    @Test
    fun `fetchUser returns correct data`() {
        val repository = UserRepository(FakeApi())

        val result = runBlocking {
            repository.fetchUser("123")
        }

        assertEquals("John", result.name)
        assertEquals("john@test.com", result.email)
    }
}

callback और suspend दुनियाओं के बीच पुल के लिए, callbacks के बजाय runBlocking के साथ CompletableDeferred का उपयोग करें — यह असिंक्रोनस ऑपरेशन चेन को सरल करता है और कोड पठनीयता में सुधार करता है।

दुरुपयोग के खतरे

runBlocking का अनुचित उपयोग ब्लॉकिंग दृष्टिकोण से कोरूटीन में स्थानांतरित होते समय सामान्य गलतियों में से एक है। मुख्य समस्याएँ: Android के मुख्य थ्रेड पर कॉल करना, runBlocking को एक दूसरे के अंदर नेस्ट करना, असिंक्रोनस फ़ंक्शन के अंदर उपयोग करना और runBlocking के माध्यम से लंबे ऑपरेशन शुरू करना।

  • ANR — Android के मुख्य थ्रेड पर runBlocking UI रेंडरिंग को 5 सेकंड से अधिक के लिए ब्लॉक करता है
  • डेडलॉक — एक ही थ्रेड पर एक कोरूटीन के अंदर नेस्टेड runBlocking आपसी ब्लॉकिंग का कारण बनता है
  • डिस्पैचर भ्रम — बैकग्रउंड थ्रेड पर runBlocking के अंदर Dispatchers.Main में Looper नहीं है और एक्सेप्शन फेंकता है
  • मेमोरी लीक — Activity/Fragment नष्ट होने पर runBlocking स्वचालित रद्द नहीं होता

सुनहरी नियम: runBlocking एक पुल है, बदलाव नहीं। इसे केवल blocking और non-blocking दुनियाओं को जोड़ने के लिए उपयोग करें। अन्य सभी कार्यों के लिए, launch, async या lifecycleScope का उपयोग करें।

अक्सर पूछे जाने वाले प्रश्न

runBlocking थ्रेड को क्यों ब्लॉक करता है जबकि अन्य बिल्डर नहीं करते?

runBlocking एकमात्र बिल्डर है जो suspend फ़ंक्शन नहीं है। यह वर्तमान थ्रेड पर एक event-loop शुरू करता है और जब तक सभी कोरूटीन पूरी नहीं हो जातीं, नियंत्रण वापस नहीं करता। launch और async तुरंत नियंत्रण लौटाते हैं, कोरूटीन को पृष्ठभूमि में निष्पादित करते हैं।

क्या runBlocking का उपयोग Android ViewModel में किया जा सकता है?

अनुशंसित नहीं। ViewModel में एक निर्मित viewModelScope है जो स्वचालित रूप से कोरूटीन का प्रबंधन करता है और नष्ट होने पर उन्हें रद्द करता है। ViewModel में runBlocking थ्रेड को ब्लॉक करता है और लाइफसाइकल रद्दीकरण का जवाब नहीं देता।

यूनिट परीक्षणों में runBlocking की जगह क्या उपयोग करें?

kotlinx-coroutines-test लाइब्रेरी से runTest का उपयोग करें। यह आभासी समय नियंत्रण, स्वचालित रद्दीकरण और निर्धार्यिक निष्पादन के साथ TestCoroutineScope प्रदान करता है।

runBlocking में event-loop क्या है?

Event-loop runBlocking के अंदर एक ईवेंट प्रोसेसिंग चक्र है। जब कोई कोरूटीन निलंबित होती है (जैसे delay()), event-loop उसी थ्रेड पर अन्य तैयार कोरूटीन के निष्पादन पर स्विच करता है। यह थ्रेड स्विचिंग के बिना मल्टिटास्किंग का भ्रम पैदा करता है।

runBlocking के अंदर runBlocking कॉल करने पर क्या होता है?

एक ही थ्रेड पर नेस्टेड runBlocking एक डेडलॉक बनाता है — बाहरी ब्लॉक आंतरिक का इंतजार करता है, लेकिन आंतरिक बाहरी के समाप्त होने तक शुरू नहीं हो सकता। अलग-अलग थ्रेड पर इसकी अनुमति है लेकिन डिबगिंग जटिलता के कारण दृढ़ता से हतोत्साहित नहीं है।

सारांश

  • runBlocking — एक ब्लॉकिंग Coroutine Builder, blocking और async कोड के बीच पुल
  • Event-loop runBlocking बिना स्विचिंग के एक ही थ्रेड पर सहकारी रूप से कोरूटीन को प्रोसेस करता है
  • अनुमत परिदृश्य — main(), JUnit परीक्षण, callback लाइब्रेरियों से पुल
  • निषिद्ध परिदृश्य — Android UI थ्रेड, नेस्टेड कॉल, लंबे ऑपरेशन
  • विकल्प — lifecycleScope, viewModelScope, परीक्षणों के लिए runTest
  • ANR जोखिम — मुख्य थ्रेड पर runBlocking 5 सेकंड के बाद एप्लिकेशन फ्रीज़ का कारण बनता है
  • प्रोडक्शन Android कोड के लिए, async बिल्डर का उपयोग करें — runBlocking UI के लिए डिजाइन नहीं किया गया है

हम एक मोबाइल एप्लिकेशन टर्नकी विकसित करेंगे

IT Sectr 2017 से स्टार्टअप और व्यवसायों के लिए iOS और Android एप्लिकेशन बनाता है। हम आपको सलाह देंगे और सर्वोत्तम समाधान प्रस्तावित करेंगे।

परियोजना पर चर्चा करें

यह भी पढ़ें