Theory
Smarter Navigation और Shared State
Basic routing एक URL को एक component में map करती है। Real apps को ज़्यादा चाहिए: heavy pages सिर्फ़ visit होने पर load करना, unauthorised users को एक page तक पहुँचने से रोकना, एक half-filled form छोड़ने से पहले warn करना, और page appear होते ही data ready रखना। और app के across components को अक्सर same changing state share करनी होती है, जैसे कौन logged in है।
Angular इसके लिए चार tools provide करता है: lazy loading, route guards, resolvers, और RxJS Subjects। यह lesson हर एक introduce करता है, तो FestConnect intelligently navigate कर सके और अपनी state sync में रख सके।
At a glance
| Tool | यह क्या करता है |
|---|---|
| Lazy Loading | सिर्फ़ जब user वहाँ navigate करता है तब एक route का code load करता है (smaller initial load) |
| CanActivate Guard | Decide करता है एक route ENTER हो सकता है या नहीं (जैसे logged in होना ज़रूरी) |
| CanDeactivate Guard | Decide करता है user LEAVE कर सकता है या नहीं (जैसे unsaved changes के बारे में warn करना) |
| Resolver | Route activate होने से PEHLE data fetch करता है, तो page के पास यह ready है |
| RxJS Subject / BehaviorSubject | Components के across changing state share करता है (BehaviorSubject एक current value भी hold करता है) |
Practical
Lazy Loading और एक Functional Route Guard
import { Routes } from '@angular/router';
import { inject } from '@angular/core';
import { AuthService } from './auth.service';
// A functional CanActivate guard (Angular 17 style)
const authGuard = () => inject(AuthService).isLoggedIn();
export const routes: Routes = [
{ path: 'events', loadComponent: () => // lazy: loaded on demand
import('./events/events.component').then(m => m.EventsComponent) },
{ path: 'profile', canActivate: [authGuard], // blocked unless logged in
loadComponent: () =>
import('./profile/profile.component').then(m => m.ProfileComponent) },
];Theory
Guards, Resolvers, और ये क्यों Help करते हैं
CanActivate एक route load होने से पहले चलता है और true या false return करता है: FestConnect /profile को block कर सकता है जब तक user logged in न हो। CanDeactivate तब चलता है जब user leave करने की कोशिश करता है: अगर registration form में उनके unsaved changes हैं, यह पहले उन्हें warn कर सकता है। Resolvers एक route का data advance में fetch करते हैं, तो events page अपनी list already loaded के साथ open होता है, empty screen का कोई flash नहीं।
साथ में ये navigation को deliberate और safe feel कराते हैं: right people right pages तक पहुँचते हैं, right time पर, data ready के साथ।
Practical
Shared State के लिए BehaviorSubject (Current User)
import { Injectable } from '@angular/core';
import { BehaviorSubject } from 'rxjs';
@Injectable({ providedIn: 'root' })
export class AuthService {
// BehaviorSubject holds a CURRENT value and emits it to new subscribers
private userSubject = new BehaviorSubject<string | null>(null);
user$ = this.userSubject.asObservable();
login(name: string) { this.userSubject.next(name); } // push a new value
logout() { this.userSubject.next(null); }
}
// Any component can subscribe to user$ and always get the latest logged-in user.Quiz
आप चाहते हैं users जब तक logged in न हों /profile page open न कर सकें। कौन सा routing tool fit करता है?
- एक resolver, क्योंकि यह data fetch करता है
- एक CanActivate guard, जो decide करता है एक route enter हो सकता है या नहीं
- Lazy loading, क्योंकि यह page hide करता है
- एक CanDeactivate guard, क्योंकि यह leaving control करता है
Show the answer
एक CanActivate guard, जो decide करता है एक route enter हो सकता है या नहीं
एक CanActivate guard एक route enter होने से पहले चलता है और true या false return करता है, तो यह exactly वह है जो /profile को block करता है जब तक user logged in न हो। Option A, एक resolver, एक route के लिए DATA pre-fetch करता है; यह decide नहीं करता entry allowed है या नहीं। Option C, lazy loading, performance के लिए एक route का code कब load होता है (on demand) यह control करता है; यह access rules enforce नहीं करता। Option D, CanDeactivate, एक route LEAVING control करता है (जैसे unsaved changes के बारे में warn करना), जो यहाँ जो हमें चाहिए उसकी opposite direction है। एक route में entering CanActivate से guarded है; leaving CanDeactivate से।
Think first
एक BehaviorSubject Shared App State के लिए एक Plain Subject से Better क्यों Suit करता है?
एक Subject और एक BehaviorSubject दोनों values broadcast करते हैं। Current user जैसी state के लिए BehaviorSubject को क्यों prefer करें? फिर tap कीजिए।
Show the answer
क्योंकि एक BehaviorSubject अपनी CURRENT value याद रखता है और इसे उस किसी भी component को immediately देता है जो बाद में subscribe करता है, जबकि एक plain Subject सिर्फ़ उन्हें emit करता है जो एक value push होने के moment already listening हैं। FestConnect में logged-in user सोचिए। मान लीजिए user early login करता है, और फिर कहीं और एक component (एक navbar, एक profile widget) यह पता लगाने के लिए बाद में subscribe करता है कौन logged in है। एक plain Subject के साथ, वह late subscriber तब तक कुछ नहीं सुनेगा जब तक NEXT बार एक value push न हो, तो इसे तब तक user का पता नहीं चलेगा जब तक वे फिर login या logout न करें, UI को out of sync छोड़ते हुए। एक BehaviorSubject, contrast में, एक current value के साथ created होता है (या hold करता है) और हर new subscriber को इनके subscribe करते ही वह latest value replay करता है, तो navbar immediately सीखता है user पहले से logged in है। वह 'हमेशा hand out करने के लिए एक current value होना' behaviour exactly वह है जो shared STATE को चाहिए: state एक ऐसी चीज़ है जिसकी हर समय एक value है, और पूछने वाले किसी भी component को present value मिलनी चाहिए, सिर्फ़ future changes नहीं। एक plain Subject one-off EVENTS (एक button click, एक notification) के लिए better है जहाँ replay करने के लिए कोई meaningful 'current value' नहीं है। तो rule of thumb है: state के लिए BehaviorSubject (current value matter करती है), events के लिए Subject (सिर्फ़ moment matter करता है)। Current-value replay ही है जो BehaviorSubject को app state के लिए right tool बनाता है।
Summary
Key takeaways
- Lazy loading सिर्फ़ जब user वहाँ navigate करता है तब एक route का code load करता है, initial bundle shrink करते हुए।
- CanActivate guards decide करते हैं एक route enter हो सकता है या नहीं (जैसे logged in होना ज़रूरी); Angular 17 functional guards इस्तेमाल करता है।
- CanDeactivate guards decide करते हैं user leave कर सकता है या नहीं (जैसे unsaved changes के बारे में warn करना)।
- Resolvers एक route activate होने से पहले इसका data fetch करते हैं, तो page data ready के साथ open होता है।
- RxJS Subjects components के across changing state share करते हैं; एक BehaviorSubject एक current value भी hold करता है।
- BehaviorSubject app state को suit करता है (current user जैसी) क्योंकि यह new subscribers को latest value replay करता है।
- Memory hook: speed के लिए lazy-load, access के लिए guards, data के लिए resolvers, shared state के लिए BehaviorSubject।