रिॲक्ट कॉनकरंट शेड्युलिंगचा सखोल अभ्यास, प्रायॉरिटी लेन्स, इंटरप्शन हँडलिंग आणि जटिल ॲप्लिकेशन्ससाठी कार्यक्षमता कशी ऑप्टिमाइझ करावी याचे अन्वेषण. या शक्तिशाली रिॲक्ट फीचरसह अधिक स्मूथ आणि प्रतिसाद देणारे UI कसे बनवायचे ते शिका.
रिॲक्ट कॉनकरंट शेड्युलिंग: प्रायॉरिटी लेन्स आणि इंटरप्शन हँडलिंगमध्ये प्राविण्य
रिॲक्ट कॉनकरंट शेड्युलिंग (React Concurrent Scheduling), जे रिॲक्ट 18 आणि त्यानंतरच्या आवृत्त्यांचे एक प्रमुख वैशिष्ट्य आहे, रिॲक्ट ॲप्लिकेशन्स अपडेट्स कसे व्यवस्थापित करतात आणि रेंडर करतात यात एक मोठे बदल दर्शवते. हे अधिक प्रतिसाद देणारे आणि कार्यक्षम यूजर इंटरफेसची क्षमता उघड करते, विशेषतः अशा जटिल ॲप्लिकेशन्समध्ये जेथे दीर्घकाळ चालणारी कार्ये मुख्य थ्रेडला ब्लॉक करू शकतात, ज्यामुळे वापरकर्त्याचा अनुभव निराशाजनक होऊ शकतो. हे विस्तृत मार्गदर्शक कॉनकरंट शेड्युलिंगच्या बारकाव्यांचा शोध घेईल, ज्यामध्ये प्रायॉरिटी लेन्स, इंटरप्शन हँडलिंग आणि आपल्या रिॲक्ट ॲप्लिकेशन्सला ऑप्टिमाइझ करण्यासाठी व्यावहारिक धोरणे यांचा समावेश आहे.
रिॲक्ट कॉनकरंट शेड्युलिंग समजून घेणे
कॉनकरंट शेड्युलिंगपूर्वी, रिॲक्ट प्रामुख्याने सिंक्रोनस (synchronous) पद्धतीने काम करत होते. जेव्हा एखादे अपडेट व्हायचे, तेव्हा रिॲक्ट लगेचच रिकन्सिलिएशन (reconciliation) प्रक्रिया सुरू करायचे, ज्यामुळे मुख्य थ्रेड ब्लॉक होऊ शकत होता आणि ब्राउझरला वापरकर्त्याच्या कृतींना प्रतिसाद देण्यापासून रोखू शकत होता. यामुळे लक्षणीय विलंब आणि एक जर्की (janky) UI दिसू शकत होता.
कॉनकरंट शेड्युलिंग एक नवीन दृष्टिकोन सादर करते. रिॲक्ट आता रेंडरिंगच्या कामांना लहान, थांबवता येण्याजोग्या (interruptible) युनिट्समध्ये विभागू शकते. यामुळे रिॲक्टला त्यांच्या प्राधान्यानुसार आणि ॲप्लिकेशनच्या प्रतिसादाच्या गरजेनुसार रेंडरिंगची कामे थांबवता, पुन्हा सुरू करता किंवा सोडून देता येतात. हे आपल्या UI अपडेट्ससाठी एका अत्यंत कार्यक्षम टास्क मॅनेजरसारखे आहे.
मुख्य संकल्पना:
- कॉनकरंट मोड (Concurrent Mode): रिॲक्टच्या वैशिष्ट्यांच्या समूहासाठी वापरला जाणारा सर्वसमावेशक शब्द, जो कॉनकरंट रेंडरिंगला सक्षम करतो.
- प्रायॉरिटी लेन्स (Priority Lanes): विविध प्रकारच्या अपडेट्सना वेगवेगळी प्राधान्ये देण्याची यंत्रणा.
- इंटरप्टिबल रेंडरिंग (Interruptible Rendering): अधिक महत्त्वाच्या अपडेट्सना प्राधान्य देण्यासाठी रिॲक्ट रेंडरिंगची कामे थांबवू आणि पुन्हा सुरू करू शकते.
- सस्पेन्स (Suspense): डेटा फेचिंगसारख्या असिंक्रोनस (asynchronous) ऑपरेशन्सना डिक्लेरेटिव्ह (declarative) पद्धतीने हाताळण्याची यंत्रणा, ज्यामुळे तुमच्या ॲप्लिकेशनचा अनुभव अधिक चांगला होतो.
- ट्रान्झिशन्स (Transitions): एक वैशिष्ट्य जे तुम्हाला काही स्टेट अपडेट्सना तातडीचे नाहीत असे चिन्हांकित करण्याची परवानगी देते, ज्यामुळे रिॲक्ट अधिक महत्त्वाच्या कृतींना प्राधान्य देऊ शकते.
प्रायॉरिटी लेन्स: अपडेटच्या तातडीचे व्यवस्थापन
प्रायॉरिटी लेन्स कॉनकरंट शेड्युलिंगचा केंद्रबिंदू आहेत. त्या वापरकर्त्याच्या अनुभवावरील महत्त्व आणि परिणामावर आधारित अपडेट्सचे वर्गीकरण करण्याचा एक मार्ग प्रदान करतात. रिॲक्ट नंतर या प्राधान्यांचा वापर करून ठरवते की कोणते अपडेट्स प्रथम प्रोसेस करायचे आणि त्यांना किती वेगाने रेंडर करायचे.
याची कल्पना एका महामार्गाप्रमाणे करा ज्यात वेगवेगळ्या प्रकारच्या वाहतुकीसाठी वेगवेगळ्या लेन्स आहेत. आपत्कालीन वाहनांना (उच्च-प्राधान्य अपडेट्स) सर्वात वेगवान लेन मिळते, तर कमी गतीची वाहतूक (कमी-प्राधान्य अपडेट्स) इतर लेन्स वापरते.
सामान्य प्रायॉरिटी लेव्हल्स:
- इमिजिएट प्रायॉरिटी (Immediate Priority): ज्या अपडेट्सवर त्वरित प्रक्रिया करणे आवश्यक आहे, जसे की वापरकर्त्याच्या इनपुट इव्हेंट्स (उदा., टेक्स्ट फील्डमध्ये टाइप करणे).
- यूझर-ब्लॉकिंग प्रायॉरिटी (User-Blocking Priority): जे अपडेट्स वापरकर्त्याला UI शी संवाद साधण्यापासून रोखतात.
- नॉर्मल प्रायॉरिटी (Normal Priority): बहुतेक अपडेट्ससाठी डिफॉल्ट प्राधान्य.
- लो प्रायॉरिटी (Low Priority): जे अपडेट्स वापरकर्त्याच्या अनुभवासाठी गंभीर नाहीत आणि पुढे ढकलले जाऊ शकतात.
- आयडल प्रायॉरिटी (Idle Priority): जे अपडेट्स ब्राउझर निष्क्रिय असताना केले जाऊ शकतात.
तुम्ही प्रत्येक अपडेटसाठी थेट प्राधान्य पातळी निर्दिष्ट करू शकत नसला तरी, रिॲक्ट ज्या संदर्भात अपडेट होते त्यावरून प्राधान्य ठरवते. उदाहरणार्थ, इव्हेंट हँडलर्स (उदा., `onClick`, `onChange`) द्वारे ट्रिगर झालेल्या अपडेट्सना साधारणपणे `setTimeout` किंवा `setInterval` द्वारे ट्रिगर झालेल्या अपडेट्सपेक्षा जास्त प्राधान्य दिले जाते.
लो-प्रायॉरिटी अपडेट्ससाठी ट्रान्झिशन्सचा वापर
`useTransition` हुक काही स्टेट अपडेट्सना स्पष्टपणे कमी-प्राधान्य म्हणून चिन्हांकित करण्याचा एक शक्तिशाली मार्ग प्रदान करतो. हे विशेषतः ॲनिमेशन्स, UI ट्रान्झिशन्स आणि इतर तातडीच्या नसलेल्या अपडेट्ससाठी उपयुक्त आहे, जे वापरकर्त्याच्या अनुभवावर नकारात्मक परिणाम न करता पुढे ढकलले जाऊ शकतात.
येथे एक उदाहरण आहे:
import { useState, useTransition } from 'react';
function MyComponent() {
const [isPending, startTransition] = useTransition();
const [text, setText] = useState('');
const handleChange = (e) => {
startTransition(() => {
setText(e.target.value);
});
};
return (
{isPending ? Updating...
: Text: {text}
}
);
}
या उदाहरणात, `setText` अपडेट `startTransition` मध्ये गुंडाळलेले आहे. हे रिॲक्टला सांगते की या अपडेटला कमी-प्राधान्य समजावे. जर ब्राउझर व्यस्त असेल, तर रिॲक्ट मुख्य थ्रेड ब्लॉक होण्यापासून टाळण्यासाठी अपडेटला विलंब करू शकते. `isPending` फ्लॅग वापरकर्त्याला लोडिंग इंडिकेटर दाखवण्यासाठी वापरला जाऊ शकतो.
इंटरप्शन हँडलिंग: यूझरच्या कृतींना प्रतिसाद देणे
कॉनकरंट शेड्युलिंगचा एक महत्त्वाचा फायदा म्हणजे जेव्हा उच्च-प्राधान्याचे अपडेट येते तेव्हा दीर्घकाळ चालणाऱ्या रेंडरिंग कार्यांना थांबवण्याची (interrupt) क्षमता. हे सुनिश्चित करते की UI वापरकर्त्याच्या कृतींना प्रतिसाद देत राहते, जरी कॉम्प्लेक्स कंपोनंट्स रेंडर होत असले तरीही.
एका अशा परिस्थितीची कल्पना करा जिथे तुम्ही आयटम्सची एक मोठी यादी रेंडर करत आहात. जसा वापरकर्ता यादीतून स्क्रोल करतो, रिॲक्टला दिसणारे आयटम्स दाखवण्यासाठी UI अपडेट करण्याची आवश्यकता असते. कॉनकरंट शेड्युलिंगशिवाय, संपूर्ण यादी रेंडर केल्याने मुख्य थ्रेड ब्लॉक होऊ शकतो, ज्यामुळे स्क्रोलिंग जर्की वाटू शकते. कॉनकरंट शेड्युलिंगसह, रिॲक्ट वापरकर्ता स्क्रोल करतो तेव्हा यादीचे रेंडरिंग थांबवू शकते, स्क्रोल इव्हेंटला प्राधान्य देते आणि एक स्मूथ स्क्रोलिंग अनुभव सुनिश्चित करते.
इंटरप्शन कसे काम करते:
- रिॲक्ट एक कंपोनंट ट्री रेंडर करण्यास सुरुवात करते.
- जर उच्च-प्राधान्याचे अपडेट आले (उदा., वापरकर्त्याने क्लिक केले किंवा की दाबले), तर रिॲक्ट सध्याचे रेंडरिंग कार्य थांबवते.
- रिॲक्ट उच्च-प्राधान्याच्या अपडेटवर प्रक्रिया करते.
- जेव्हा उच्च-प्राधान्याचे अपडेट पूर्ण होते, तेव्हा रिॲक्ट थांबवलेले रेंडरिंग कार्य पुन्हा सुरू करू शकते किंवा पूर्णपणे सोडून देऊ शकते, हे थांबवलेले कार्य अजूनही संबंधित आहे की नाही यावर अवलंबून असते.
ही इंटरप्शन यंत्रणा रिॲक्टला ॲप्लिकेशनच्या सध्याच्या गरजांनुसार आपली रेंडरिंग धोरण गतिशीलपणे समायोजित करण्याची परवानगी देते, ज्यामुळे वापरकर्त्याचा अनुभव स्मूथ आणि प्रतिसाद देणारा राहतो.
सस्पेन्स: डिक्लेरेटिव्ह डेटा फेचिंग आणि लोडिंग स्टेट्स
सस्पेन्स हे आणखी एक शक्तिशाली वैशिष्ट्य आहे जे कॉनकरंट शेड्युलिंगसह अखंडपणे कार्य करते. हे तुम्हाला डेटा फेचिंगसारख्या असिंक्रोनस ऑपरेशन्सना डिक्लेरेटिव्ह पद्धतीने हाताळण्याची परवानगी देते, ज्यामुळे तुमचा कोड अधिक स्वच्छ आणि समजण्यास सोपा होतो. डेटा लोड होत असताना फॉलबॅक कंटेंट दाखवून सस्पेन्स तुमच्या ॲप्लिकेशनच्या अनुभवाची गुणवत्ता सुधारते.
पारंपारिकपणे, रिॲक्टमध्ये डेटा फेचिंगसाठी लोडिंग स्टेट्स आणि एरर हँडलिंग मॅन्युअली व्यवस्थापित करावे लागत होते. यामुळे अनेकदा कोड कॉम्प्लेक्स आणि मोठा होत असे. सस्पेन्स असिंक्रोनस डेटावर अवलंबून असलेल्या कंपोनंट्सना `Suspense` बाउंड्रीमध्ये गुंडाळून ही प्रक्रिया सोपी करते. त्यानंतर तुम्ही डेटा लोड होत असताना दाखवण्यासाठी एक फॉलबॅक कंपोनंट निर्दिष्ट करू शकता.
येथे एका काल्पनिक `fetchData` फंक्शनचा वापर करून एक उदाहरण आहे:
import { Suspense } from 'react';
function MyComponent() {
const data = fetchData(); // This might throw a Promise
return (
{data.title}
{data.description}
);
}
function App() {
return (
Loading...}>
);
}
या उदाहरणात, जर `fetchData` ने एक प्रॉमिस (Promise) परत केले (जे दर्शवते की डेटा अद्याप उपलब्ध नाही), तर रिॲक्ट `MyComponent` चे रेंडरिंग थांबवेल आणि प्रॉमिस पूर्ण होईपर्यंत फॉलबॅक कंपोनंट (`
Loading...
`) दाखवेल. एकदा डेटा उपलब्ध झाल्यावर, रिॲक्ट मिळवलेल्या डेटासह `MyComponent` चे रेंडरिंग पुन्हा सुरू करेल.सस्पेन्स कॉनकरंट शेड्युलिंगसह उत्कृष्टपणे कार्य करते. जेव्हा एखादा कंपोनंट सस्पेंड होतो, तेव्हा रिॲक्ट रेंडरिंग प्रक्रिया थांबवू शकते आणि इतर कामांवर लक्ष केंद्रित करू शकते. यामुळे रिॲक्टला डेटा लोड होण्याची वाट पाहत असताना अधिक महत्त्वाच्या अपडेट्सना प्राधान्य देण्याची संधी मिळते, ज्यामुळे ॲप्लिकेशनचा एकूण प्रतिसाद सुधारतो.
कॉनकरंट शेड्युलिंगसह रिॲक्ट ॲप्लिकेशन्स ऑप्टिमाइझ करणे
कॉनकरंट शेड्युलिंगचे पूर्ण फायदे घेण्यासाठी, आपल्या रिॲक्ट ॲप्लिकेशन्सला ऑप्टिमाइझ करण्यासाठी सर्वोत्तम पद्धतींचा अवलंब करणे आवश्यक आहे.
मुख्य ऑप्टिमायझेशन स्ट्रॅटेजीज:
- अनावश्यक री-रेंडर्स कमी करा: `React.memo`, `useMemo`, आणि `useCallback` चा वापर करून कंपोनंट्सना त्यांचे प्रॉप्स बदलले नसताना री-रेंडर होण्यापासून प्रतिबंधित करा. विशेषतः कॉम्प्लेक्स स्टेटसाठी अपरिवर्तनीय (immutable) डेटा स्ट्रक्चर्सचा वापर करण्याचा विचार करा.
- डेटा फेचिंग ऑप्टिमाइझ करा: कॅशिंग आणि पेजिनेशनसारख्या कार्यक्षम डेटा फेचिंग तंत्रांचा वापर करून फेच आणि रेंडर होणाऱ्या डेटाचे प्रमाण कमी करा. `swr` आणि `react-query` सारखी साधने ही प्रक्रिया मोठ्या प्रमाणात सोपी करू शकतात.
- मोठे कंपोनंट्स विभाजित करा: मोठ्या, कॉम्प्लेक्स कंपोनंट्सना लहान, अधिक व्यवस्थापित करण्यायोग्य कंपोनंट्समध्ये विभाजित करा. यामुळे रेंडरिंगची कार्यक्षमता सुधारू शकते आणि तुमचा कोड समजण्यास आणि सांभाळण्यास सोपा होऊ शकतो.
- CPU-इंटेंसिव्ह कामांसाठी वेब वर्कर्सचा वापर करा: इमेज प्रोसेसिंग किंवा कॉम्प्लेक्स कॅल्क्युलेशन्ससारखी CPU-इंटेंसिव्ह कामे वेब वर्कर्सकडे सोपवा जेणेकरून ते मुख्य थ्रेडला ब्लॉक करणार नाहीत.
- आपल्या ॲप्लिकेशनचे प्रोफाइल करा: परफॉर्मन्स बॉटलनेक्स आणि ऑप्टिमायझेशनसाठी क्षेत्रे ओळखण्यासाठी रिॲक्ट प्रोफाइलरचा वापर करा. तुमच्या कोडचा रेंडर सायकलवरील परिणाम समजून घ्या.
- इव्हेंट हँडलर्सना डीबाउन्स आणि थ्रॉटल करा: जास्त अपडेट्स टाळण्यासाठी इव्हेंट हँडलर्स कार्यान्वित होण्याचा दर मर्यादित करा. उदाहरणार्थ, शोध इनपुटसह, तुम्ही वापरकर्त्याने थोड्या काळासाठी टाइप करणे थांबवल्यानंतरच शोध सुरू करू शकता.
आंतरराष्ट्रीय बाबी:
- लोकलायझेशन (l10n): तुमचे ॲप्लिकेशन विविध भाषा आणि सांस्कृतिक संदर्भ हाताळू शकते याची खात्री करा. भाषांतरे व्यवस्थापित करण्यासाठी आणि तुमच्या UI ला वेगवेगळ्या लोकेल्समध्ये जुळवून घेण्यासाठी आंतरराष्ट्रीयीकरण लायब्ररी (उदा., `i18next`) वापरा.
- तारीख आणि वेळ स्वरूपन: वापरकर्त्याच्या लोकेलनुसार योग्य तारीख आणि वेळ स्वरूपन वापरा. `date-fns` आणि `moment.js` (जरी त्याचा आकार आणि नापसंतपणामुळे पर्याय विचारात घ्या) सारख्या लायब्ररी यात मदत करू शकतात.
- संख्या आणि चलन स्वरूपन: वापरकर्त्याच्या लोकेलनुसार संख्या आणि चलने स्वरूपित करा.
- उजवीकडून-डावीकडे (RTL) लेआउट: CSS लॉजिकल प्रॉपर्टीज आणि RTL लेआउट ट्रान्सफॉर्मेशन हाताळणाऱ्या लायब्ररी वापरून RTL भाषांना (उदा., अरबी, हिब्रू) समर्थन द्या.
- ॲक्सेसिबिलिटी (a11y): ॲक्सेसिबिलिटी मार्गदर्शक तत्त्वांचे पालन करून आणि ARIA ॲट्रिब्यूट्स वापरून तुमचे ॲप्लिकेशन अपंग वापरकर्त्यांसाठी ॲक्सेसिबल असल्याची खात्री करा.
वास्तविक-जगातील उदाहरणे आणि उपयोग
चला काही वास्तविक-जगातील उदाहरणे पाहूया की कॉनकरंट शेड्युलिंगचा वापर रिॲक्ट ॲप्लिकेशन्सची कार्यक्षमता सुधारण्यासाठी कसा केला जाऊ शकतो.
उदाहरण १: कॉम्प्लेक्स डेटा व्हिज्युअलायझेशन
जे ॲप्लिकेशन्स चार्ट्स आणि ग्राफ्ससारखे कॉम्प्लेक्स डेटा व्हिज्युअलायझेशन दाखवतात, त्यात अनेकदा मोठ्या संख्येने एलिमेंट्स रेंडर करावे लागतात. कॉनकरंट शेड्युलिंगशिवाय, हे व्हिज्युअलायझेशन रेंडर करणे धीमे आणि प्रतिसादहीन असू शकते. कॉनकरंट शेड्युलिंग आणि व्हर्च्युअलायझेशनसारख्या (व्हिज्युअलायझेशनचे फक्त दिसणारे भाग रेंडर करणे) तंत्रांचा वापर करून, तुम्ही या ॲप्लिकेशन्सची कार्यक्षमता आणि प्रतिसाद लक्षणीयरीत्या सुधारू शकता.
उदाहरण २: रिअल-टाइम डेटा डॅशबोर्ड
सतत अपडेट होणारा डेटा स्ट्रीम दाखवणारे रिअल-टाइम डेटा डॅशबोर्ड वापरकर्त्याच्या कृतींना अत्यंत प्रतिसाद देणारे असणे आवश्यक आहे. कॉनकरंट शेड्युलिंग तुम्हाला डेटा अपडेट्सपेक्षा वापरकर्त्याच्या कृतींना प्राधान्य देण्याची परवानगी देते, ज्यामुळे नवीन डेटा प्राप्त होत असतानाही डॅशबोर्ड इंटरॅक्टिव्ह राहतो. डेटा अपडेट्स स्मूथ करण्यासाठी ट्रान्झिशन्सचा वापर करणे देखील उपयुक्त आहे.
उदाहरण ३: कॉम्प्लेक्स फिल्टरिंगसह ई-कॉमर्स ॲप्लिकेशन्स
ई-कॉमर्स ॲप्लिकेशन्समध्ये अनेकदा कॉम्प्लेक्स फिल्टरिंग आणि सॉर्टिंग ऑपरेशन्स असतात. जेव्हा वापरकर्ता फिल्टर लागू करतो, तेव्हा ॲप्लिकेशनला उत्पादन सूची पुन्हा रेंडर करावी लागते. कॉनकरंट शेड्युलिंगसह, तुम्ही उत्पादन सूचीचे री-रेंडरिंग कमी-प्राधान्याचे कार्य म्हणून चिन्हांकित करू शकता, ज्यामुळे फिल्टरिंग होत असताना ॲप्लिकेशन वापरकर्त्याच्या कृतींना प्रतिसाद देत राहते. फिल्टरिंग प्रक्रियेदरम्यान लोडिंग इंडिकेटर दाखवणे देखील एक चांगली पद्धत आहे.
उदाहरण ४: सहयोगी डॉक्युमेंट एडिटर्स
सहयोगी डॉक्युमेंट एडिटर्सना अनेक वापरकर्त्यांकडून येणारे अपडेट्स सतत सिंक्रोनाइझ आणि रेंडर करावे लागतात. कॉनकरंट शेड्युलिंग हे अपडेट्स कार्यक्षमतेने व्यवस्थापित करण्यात मदत करू शकते, वापरकर्त्याच्या इनपुटला प्राधान्य देऊन आणि एकाच वेळी अनेक वापरकर्ते असतानाही एक स्मूथ संपादन अनुभव राखते. ऑप्टिमिस्टिक अपडेट्समुळे अनुभवाची प्रतिसादक्षमता आणखी वाढू शकते.
निष्कर्ष: उत्तम यूझर अनुभवासाठी कॉनकरंट शेड्युलिंगचा स्वीकार
रिॲक्ट कॉनकरंट शेड्युलिंग अधिक प्रतिसाद देणारे आणि कार्यक्षम रिॲक्ट ॲप्लिकेशन्स तयार करण्यासाठी एक शक्तिशाली साधन आहे. प्रायॉरिटी लेन्स, इंटरप्शन हँडलिंग, सस्पेन्स आणि ट्रान्झिशन्स या संकल्पना समजून घेऊन, तुम्ही तुमच्या ॲप्लिकेशन्सना अधिक स्मूथ आणि आकर्षक वापरकर्ता अनुभव देण्यासाठी ऑप्टिमाइझ करू शकता. जसे रिॲक्ट विकसित होत राहील, कॉनकरंट शेड्युलिंग निःसंशयपणे रिॲक्ट डेव्हलपमेंट लँडस्केपचा एक वाढता महत्त्वाचा भाग बनेल. या नवीन वैशिष्ट्ये आणि सर्वोत्तम पद्धतींचा स्वीकार करून, तुम्ही जागतिक स्तरावरील वेब ॲप्लिकेशन्स तयार करू शकता जे वापरकर्त्यांना आनंदित करतील.
कॉनकरंट शेड्युलिंगने देऊ केलेल्या शक्यतांचा प्रयोग आणि शोध घेण्यास घाबरू नका. आपल्या ॲप्लिकेशन्सचे प्रोफाइल करा, परफॉर्मन्स बॉटलनेक्स ओळखा आणि सर्वोत्तम कामगिरीसाठी आपल्या कोडमध्ये सुधारणा करा. सतत शिकून आणि आपली कौशल्ये सुधारून, तुम्ही रिॲक्ट कॉनकरंट शेड्युलिंगचे मास्टर बनू शकता आणि खरोखरच अपवादात्मक वेब ॲप्लिकेशन्स तयार करू शकता.