diff --git a/hooks/useNotificationListener.ts b/hooks/useNotificationListener.ts index c109ece..a8f4be7 100644 --- a/hooks/useNotificationListener.ts +++ b/hooks/useNotificationListener.ts @@ -1,20 +1,41 @@ +import AsyncStorage from "@react-native-async-storage/async-storage"; import * as Notifications from "expo-notifications"; import { useEffect } from "react"; import { Item } from "types/Item"; -// Hook to listen for incoming notifications and map them into Item objects -export function useNotificationListener(onItem: (item: Item) => void) { +const STORAGE_KEY = "notifications-data"; + +// Hook: listens for incoming notifications → Item + persists them +export function useNotificationListener(onItems: (items: Item[]) => void) { useEffect(() => { + // Load saved notifications on mount + (async () => { + try { + const saved = await AsyncStorage.getItem(STORAGE_KEY); + if (saved) { + const parsed: Item[] = JSON.parse(saved); + // sort newest first + onItems(parsed.sort((a, b) => b.timestamp - a.timestamp)); + } + } catch (e) { + console.error("Failed to load notifications from storage:", e); + } + })(); + // Listen for notification received while app is in foreground - const receivedSub = Notifications.addNotificationReceivedListener((notification) => { + const receivedSub = Notifications.addNotificationReceivedListener(async (notification) => { const item = mapNotificationToItem(notification); - if (item) onItem(item); + if (item) { + await addItem(item, onItems); + } }); // Listen for when user taps a notification - const responseSub = Notifications.addNotificationResponseReceivedListener((response) => { + const responseSub = Notifications.addNotificationResponseReceivedListener(async (response) => { const item = mapNotificationToItem(response.notification); - if (item) onItem(item); + if (item) { + await addItem(item, onItems); + } }); // Cleanup on unmount @@ -22,16 +43,16 @@ export function useNotificationListener(onItem: (item: Item) => void) { receivedSub.remove(); responseSub.remove(); }; - }, [onItem]); + }, [onItems]); } -// Helper: convert Expo notification → Item +// Convert Expo notification → Item function mapNotificationToItem(notification: Notifications.Notification): Item | null { try { const content = notification.request.content; return { - timestamp: Date.now(), // Or use content.data.timestamp if backend includes it + timestamp: Date.now(), // could use backend timestamp if provided category: (content.data?.category as Item["category"]) ?? "home", title: content.title ?? "No title", info: content.body ?? "No details", @@ -42,3 +63,18 @@ function mapNotificationToItem(notification: Notifications.Notification): Item | return null; } } + +// Save a new item into storage and update state +async function addItem(item: Item, onItems: (items: Item[]) => void) { + try { + const saved = await AsyncStorage.getItem(STORAGE_KEY); + const prev: Item[] = saved ? JSON.parse(saved) : []; + + const updated = [item, ...prev].sort((a, b) => b.timestamp - a.timestamp); + + await AsyncStorage.setItem(STORAGE_KEY, JSON.stringify(updated)); + onItems(updated); + } catch (e) { + console.error("Failed to persist notification:", e); + } +}