ஒவ்வொரு React டெவலப்பரும் இறுதியில் ஒரே ஒரு சுவரைச் சந்திக்க நேரிடும். உங்கள் மேல்நிலை App காம்பொனென்ட்டில் (component) ஒரு பயனர் பொருளை (user object) நீங்கள் பெறுகிறீர்கள். பிறகு அதைத் தொடர்ச்சியாகக் கீழே கடத்துகிறீர்கள். ஒரு ரூட் ரேப்பரைக் (route wrapper) கடந்து, ஒரு லேஅவுட் ஷெல் (layout shell) வழியாக, ஒரு சைட் பார் கன்டெய்னர் (sidebar container) வழியாக, மூன்று அடுக்குகள் ஆழத்தில் இருக்கும் ஒரு சிறிய அவதார் காம்பொனென்ட் ஒரு ப்ரொபைல் படத்தை காண்பிப்பதற்காக இதைச் செய்கிறீர்கள். இடையில் இருக்கும் காம்பொனென்ட்களுக்கு அந்த பயனர் பொருளின் மீது எந்த அக்காமும் இல்லை. அவை வெறும் பார்சலைத் தள்ளுபடியாக மட்டுமே கடத்துகின்றன. இதுதான் prop drilling, இது ஒரு சுத்தமான காம்பொனென்ட் மரத்தை (component tree) ஒரு குழப்பமான தகவல் மாற்ற விளையாட்டாக (game of telephone) மாற்றிவிடுகிறது.

அந்தத் தரவின் வடிவம் (shape) மாறும்போதுதான் உண்மையான சிரமம் தொடங்குகிறது. ஒருவேளை பேக்எண்ட் (backend) user.avatar-க்கு பதிலாக user.profile.avatar என்று நெஸ்டிங் (nesting) செய்யத் தொடங்கலாம். திடீரென்று, அந்தத் தரவை நேரடியாகப் பயன்படுத்தாத ஐந்து கோப்புகளில் உள்ள TypeScript இன்டர்ஃபேஸ்கள் (interfaces) அல்லது PropTypes-களை நீங்கள் மாற்ற வேண்டியிருக்கும். அங்குதான் React Context API பயன்பாட்டிற்கு வருகிறது.

Context எவ்வாறு தரவு ஓட்டத்தை (Data Flow) மாற்றியமைக்கிறது

Context-ஐ உங்கள் வீட்டின் மையத்தில் இருக்கும் ஒரு WiFi ரூட்டர் என்று நினைத்துக் கொள்ளுங்கள். அது இல்லையென்றால், உங்கள் லேப்டாப்பிற்கு சிக்னல் கிடைக்க ஒவ்வொரு அறையிலும் Ethernet கேபிள்களைக் கொண்டு செல்ல வேண்டியிருக்கும். அது இருந்தால், ரூட்டர் காற்றில் சிக்னலை பரப்புகிறது, சரியான கடவுச்சொல் உள்ள எந்தவொரு சாதனமும் நேரடியாகத் தொடர்பு கொள்ளலாம். சுவர்கள் ஒரு தடையல்ல.

React ரீதியில் கூறினால், உங்கள் ஆப்பின் ரூட் (root), ஒவ்வொரு அடுக்கையும் ஒரு கூரியர் போலச் செயல்படச் சொல்லாமல், காம்பொனென்ட் மரம் வழியாகத் தரவை பரப்ப முடியும். எந்தவொரு நெஸ்டட் காம்பொனென்ட்டும் (nested component) அந்தப் பரவலைத் தொடரலாம் (subscribe) மற்றும் அதற்குத் தேவையானதைத் துல்லியமாகப் பெறலாம்.

மூன்று முக்கியப் பகுதிகள்

Context API மூன்று முக்கியப் பகுதிகளைக் கொண்டது.

React.createContext() என்பது பரவல் சேனலை (broadcast channel) அமைக்கிறது. இது ஒரு Provider மற்றும் (பழைய கோடுகளில்) ஒரு Consumer ஆகியவற்றைக் கொண்ட ஒரு பொருளைத் திருப்பித் தருகிறது. ஒரு குறிப்பிட்ட அம்சத்திற்கு இதை நீங்கள் ஒருமுறை மட்டும் அழைக்கத் தேவையில்லை.

The Provider என்பது உங்கள் மரத்தின் ஒரு பகுதியைச் சுற்றியுள்ள ஒரு காம்பொனென்ட் ஆகும். இது value எனப்படும் ஒரு prop-ஐ ஏற்றுக்கொள்கிறது. அந்த prop-இல் நீங்கள் எதைச் சேமித்தாலும், அது எவ்வளவு ஆழமாக இருந்தாலும் அதன் கீழ் உள்ள ஒவ்வொரு வாரிசுக்கும் (descendant) கிடைக்கும்.

useContext என்பது ஒரு ஃபங்க்ஷன் காம்பொனென்ட் (function component) அந்தப் பரவலைப் பயன்படுத்த அனுமதிக்கும் ஒரு Hook ஆகும். உங்கள் காம்பொனென்ட்டிற்குள், நீங்கள் உருவாக்கிய context பொருளை useContext-க்குள் அனுப்பினால், அது தற்போதைய மதிப்பைத் திருப்பித் தரும். அவ்வளவுதான். கூடுதல் ரேப்பர்கள் (wrappers) அல்லது கூடுதல் props தேவையில்லை.

Hooks வருவதற்கு முன்பு, render props உடன் Consumer பேட்டர்னைப் பயன்படுத்த வேண்டியிருந்தது. அது வேலை செய்தது, ஆனால் அது அதிகப்படியான இண்டன்டேஷன் (indentation) மற்றும் ரேப்பர் குழப்பங்களை உருவாக்கியது. useContext இவை அனைத்தையும் உங்கள் ஃபங்க்ஷன் உடலுக்குள் ஒரு வரியாகச் சுருக்கியது.

Context எப்போது உண்மையில் பயனுள்ளதாக இருக்கும்

பழக்கத்தின் காரணமாக Context-ஐப் பயன்படுத்தாதீர்கள். இது உங்கள் மரத்தின் வெவ்வேறு கிளைகளில் உள்ள பல தொடர்பற்ற காம்பொனென்ட்கள் பகிர்ந்து கொள்ளும் தரவிற்காக உருவாக்கப்பட்டது. சிறந்த உதாரணங்கள்:

  • Theme settings. வெறும் light அல்லது dark mode மட்டுமல்ல, spacing tokens, color palettes மற்றும் font scales. இவற்றை ஒவ்வொரு ஸ்டைல் செய்யப்பட்ட பட்டன் மற்றும் மோடல் (modal) வழியாகத் தள்ளுவது விரைவில் சலிப்பை ஏற்படுத்தும்.
  • User authentication. லாகின் நிலை (Login status), அனுமதிகள் வரிசை (permissions array), அல்லது தற்போதைய பயனர் பொருள். உங்கள் ஹெடர் பார் (header bar), ஒரு டேஷ்போர்டு விட்ஜெட் (dashboard widget) மற்றும் ஒரு பிரைவேட் ரூட் கார்டு (private route guard) ஆகியவை மரத்தின் வெவ்வேறு மூலைகளில் இருக்கலாம்.
  • Language preferences. லோக்கல் ஸ்ட்ரிங்ஸ் (Locale strings), தேதி வடிவங்கள் மற்றும் கரன்சி குறியீடுகள். ஃபார்ம் லேபிள்கள் போன்ற ஆழமான காம்பொனென்ட்களுக்கு இவை தேவைப்படும், ஆனால் பாதையில் உள்ள ஒவ்வொரு பெற்றோர் காம்பொனென்ட்டிற்கும் இதைப் பற்றித் தெரிய வேண்டிய அவசியமில்லை.
  • Shopping cart data. ஐட்டம் எண்ணிக்கை, மொத்த மதிப்பு மற்றும் add-to-cart செயல்பாடுகள். ஹெடர் பேட்ஜ் (header badge) மற்றும் செக்அவுட் பக்கம் ஆகிய இரண்டிற்கும் ஒரே ஸ்டேட் (state) தேவைப்படும், ஆனால் அவை பொதுவாக முற்றிலும் மாறுபட்ட லேஅவுட் கிளைகளின் கீழ் அமையும்.

ஒரு நடைமுறை தீம் ஸ்விட்சர் (Theme Switcher)

Context-ஐச் செயல்படுத்துவதைப் பார்க்க மிகத் தெளிவான வழி ஒரு தீம் டாக்லி (theme toggle) ஆகும். முக்கியமான விவரங்களைத் தவிர்க்காமல் இதை எவ்வாறு இணைப்பது என்பதை இங்கே காணலாம்.

முதலில், ஒரு ThemeContext.js கோப்பை உருவாக்கவும். React.createContext() ஐ அழைத்து அதன் முடிவைச் சேமிக்கவும். பின்னர் useState அல்லது useReducer மூலம் தற்போதைய தீமை நிர்வகிக்கும் ஒரு ThemeProvider காம்பொனென்ட்டை உருவாக்கவும். உங்கள் context-ன் Provider-க்குள் குழந்தைகளை (children)ச் சுற்றியுங்கள், தற்போதைய தீம் மற்றும் அதை மாற்றும் (toggle) ஒரு செயல்பாட்டை உள்ளடக்கிய ஒரு பொருளை அனுப்பவும். ThemeProvider மற்றும் context பொருளை ஆகிய இரண்டையும் எக்ஸ்போர்ட் (export) செய்யவும்.

இரண்டாவதாக, உங்கள் ஆப்பின் என்ட்ரி பாயிண்டிற்குச் (app entry point) செல்லவும். ThemeProvider-ஐ இறக்குமதி செய்து (import), உங்கள் முழு அப்ளிகேஷனையும் அதனுடன் சுற்றவும். இந்தப் படிநிலையை நீங்கள் தவிர்த்தால், பின்னர் context-ஐப் படிக்க முயற்சிக்கும் எதற்கும் இயல்புநிலை மதிப்பு (default value) மட்டுமே தெரியும்.

மூன்றாவதாக, ஒரு Header அல்லது Content காம்பொனென்ட்டிற்குள், context பொருளையும் useContext-ஐயும் இறக்குமதி செய்யவும். Hook-ஐ அழைத்து, தீம் மற்றும் toggle செயல்பாட்டைப் பிரித்தெடுத்து (destructure), உங்கள் CSS வகுப்புகளை நிபந்தனைக்குட்பட்டு (conditionally) பயன்படுத்தவும். toggle-ஐ அழைக்கும் ஒரு பட்டனைச் சேர்க்கவும். இந்த காம்பொனென்ட் அதன் பெற்றோரிலிருந்து ஒரு theme prop-ஐப் பெறாது. அது சிக்னலை நேரடியாகக் காற்றில் இருந்து எடுத்துக்கொள்கிறது.

Prop Drilling, Context, அல்லது Redux?

Choosing between these tools is less about loyalty and more about the shape of your state.

Prop drilling is perfectly fine for two or three levels of depth. It is explicit, easy to trace in your IDE, and keeps dependencies obvious. The problems only show up when you start threading the same prop through six or seven layers.

Context API ships with React itself. That means no extra bundle size and no external setup. It handles small to medium global state beautifully, especially data that changes infrequently like themes or user profiles.

Redux requires installing additional libraries and writing boilerplate. It pays off when your state logic is complex, when multiple slices of state interact in deep ways, or when you need time-travel debugging and middleware. For simple global data, Redux is overkill.

The Performance Reality Nobody Talks About

Here is the catch that separates junior implementations from senior ones. When a Context Provider value changes, every component consuming that context re-renders. It does not matter if the particular slice that component cares about stayed the same. React sees the new reference and schedules an update.

If you dump your entire application state into one giant StoreContext, you have effectively glued your whole UI together. Changing a theme setting will rerender your shopping cart, your dashboard charts, and your notification list. That is unnecessary work.

Split your contexts by domain. Keep a ThemeContext for visual settings, a UserContext for profile data, and a CartContext for commerce state. If a user edits their display name, your header updates without touching the product grid. Also, be careful what you pass into the Provider value prop. If you pass an object literal { theme, toggleTheme } inline during render, you create a new reference on every render and trigger needless updates. Stabilize that shape with useMemo if the value contains functions or non-primitive data.

Mistakes That Burn Hours

Two errors catch teams again and again.

Forgetting to export the context object. It is easy to export the ThemeProvider component and then try to call useContext(ThemeProvider). That is not how it works. The Hook needs the context object returned by createContext, not the wrapper component. If you only export the Provider, your consumers have nothing to import.

Calling useContext outside its Provider. The Hook returns the default value you passed to createContext. If you did not pass a default, you get undefined. If your component tree renders the consumer higher up in the DOM than the Provider, or if the Provider is missing entirely, your data simply will not arrive. Double check that your index or root file actually wraps the app.

The Real Takeaway

React Context is not a state management revolution. It is a targeted tool for a specific spatial problem: getting data to distant components without turning every layer into a post office. Use it for genuinely global data, keep your contexts split by domain to protect rendering performance, and always wrap your tree with the correct Provider before you try to read the signal. Nail those habits, and your component trees stay clean, fast, and easy to reason about.