MediumComponent Patterns📖 Theory Question

What is the Provider pattern and how do you build a scalable context architecture?

💡

Hint

Separate state logic from context provision — custom hook for consumers, provider component for setup

Full Answer

// ─── auth-context.tsx ───────────────────────────────────────────────────────
type AuthContextValue = {
  user: User | null;
  login: (credentials: Credentials) => Promise;
  logout: () => void;
};

const AuthContext = createContext(null);

// Provider encapsulates all auth logic
export function AuthProvider({ children }: { children: ReactNode }) {
  const [user, setUser] = useState(null);

  const login = useCallback(async (creds) => {
    const user = await api.login(creds);
    setUser(user);
  }, []);

  const logout = useCallback(() => {
    api.logout();
    setUser(null);
  }, []);

  return (
    
      {children}
    
  );
}

// Custom hook — type-safe, error if used outside provider
export function useAuth() {
  const ctx = useContext(AuthContext);
  if (!ctx) throw new Error('useAuth must be used within AuthProvider');
  return ctx;
}

// ─── app layout ──────────────────────────────────────────────────────────────

  
    
      
    
  
💡 The null-check in useAuth() is critical for DX — it gives a clear error message instead of a cryptic "cannot read property of undefined" when someone forgets the provider.

Practice this in a timed sprint →

5 free questions, no signup required

⚡ Start Sprint