// src/App.jsx import { createContext, useContext, useReducer } from "react"; const NotificationContext = createContext(null); function notificationsReducer(state, action) { switch (action.type) { case "show": return [...state, { id: Date.now(), message: action.payload.message }]; case "dismiss": return state.filter((n) => n.id !== action.payload.id); default: return state; } } function NotificationProvider({ children }) { const [notifications, dispatch] = useReducer(notificationsReducer, []); return ( {children} ); } function NotificationTrigger() { const { dispatch } = useContext(NotificationContext); return ( ); } function NotificationList() { const { notifications, dispatch } = useContext(NotificationContext); return ( ); } function App() { return ( ); } export default App; /* Notes: - NotificationProvider exposes both notifications (the reducer's state) and dispatch through context — NotificationTrigger only ever needs dispatch, NotificationList needs both. - Neither consumer holds its own copy of the notifications array; both read from and update the same single reducer-managed state, exactly the useReducer + Context pairing described in the chapter. */