import React, { createContext, useContext, useState, useEffect, useRef, useCallback } from 'react';
import ticketService from '../services/ticketService';
import teamsActivityService from '../services/teamsActivityService';
import { useAuth } from './AuthContext';

const NotificationContext = createContext(null);

export const useNotifications = () => useContext(NotificationContext);

const STORAGE_KEY = 'it_notif_last_seen';
const POLL_INTERVAL = 15000; // 15 Sekunden

const PRIO_LABEL = { kritisch: '🔴 Kritisch', hoch: '🟠 Hoch', mittel: '🔵 Mittel', niedrig: '🟢 Niedrig' };

export const NotificationProvider = ({ children }) => {
    const { isAuthenticated, isSupport } = useAuth();
    const [notifications, setNotifications] = useState([]);
    const [permission, setPermission] = useState(Notification?.permission || 'default');
    const lastSeenRef = useRef(localStorage.getItem(STORAGE_KEY) || new Date().toISOString());
    const knownIdsRef = useRef(new Set());
    const pollRef = useRef(null);

    const requestPermission = useCallback(async () => {
        if (!('Notification' in window)) return;
        const result = await Notification.requestPermission();
        setPermission(result);
    }, []);

    const sendBrowserNotif = useCallback((title, body, tag) => {
        if (permission !== 'granted' || !('Notification' in window)) return;
        try {
            new Notification(title, { body, icon: '/favicon.ico', tag });
        } catch {}
    }, [permission]);

    const markAllRead = useCallback(() => {
        const now = new Date().toISOString();
        localStorage.setItem(STORAGE_KEY, now);
        lastSeenRef.current = now;
        setNotifications(prev => prev.map(n => ({ ...n, read: true })));
        teamsActivityService.markRead().catch(() => {});
    }, []);

    const markRead = useCallback((id) => {
        setNotifications(prev => prev.map(n => n.id === id ? { ...n, read: true } : n));
    }, []);

    const knownTeamsChannelIdsRef = useRef(new Set());

    const poll = useCallback(async () => {
        if (!isAuthenticated || !isSupport()) return;
        const newNotifs = [];

        // Ticket-Benachrichtigungen
        try {
            const tickets = await ticketService.getAll();
            tickets.forEach(ticket => {
                if (knownIdsRef.current.has(ticket.id)) return;
                knownIdsRef.current.add(ticket.id);
                const createdAt = ticket.created_at;
                if (createdAt > lastSeenRef.current) {
                    const notif = {
                        id: `ticket-${ticket.id}-new`,
                        type: 'new_ticket',
                        ticketId: ticket.id,
                        ticketNumber: ticket.ticket_number,
                        title: `Neues Ticket: ${ticket.title}`,
                        body: `${PRIO_LABEL[ticket.priority] || ticket.priority} · ${ticket.category}`,
                        createdAt,
                        read: false,
                        critical: ticket.priority === 'kritisch' || ticket.priority === 'hoch',
                    };
                    newNotifs.push(notif);
                    sendBrowserNotif(
                        `📋 ${ticket.ticket_number}: ${ticket.title}`,
                        `${PRIO_LABEL[ticket.priority]} · ${ticket.category}`,
                        `ticket-${ticket.id}`
                    );
                }
            });
        } catch {}

        // Teams-Kanal-Benachrichtigungen
        try {
            const newChannels = await teamsActivityService.getNewChannels();
            for (const ch of newChannels) {
                if (knownTeamsChannelIdsRef.current.has(ch.id)) continue;
                knownTeamsChannelIdsRef.current.add(ch.id);
                newNotifs.push({
                    id: `teams-channel-${ch.id}`,
                    type: 'new_teams_channel',
                    title: `Neuer Teams-Kanal: ${ch.channel_name}`,
                    body: `Team: ${ch.team_name}`,
                    createdAt: ch.first_seen_at,
                    read: false,
                    critical: false,
                });
                sendBrowserNotif(
                    `💬 Neuer Teams-Kanal: ${ch.channel_name}`,
                    `Team: ${ch.team_name}`,
                    `teams-channel-${ch.id}`
                );
            }
        } catch {}

        if (newNotifs.length > 0) {
            setNotifications(prev => [...newNotifs, ...prev].slice(0, 50));
        }
    }, [isAuthenticated, isSupport, sendBrowserNotif]);

    // Initial load + polling
    useEffect(() => {
        if (!isAuthenticated || !isSupport()) return;

        // Initial: alle bekannten IDs laden ohne Notifications zu erzeugen
        ticketService.getAll().then(tickets => {
            tickets.forEach(t => knownIdsRef.current.add(t.id));
        }).catch(() => {});

        pollRef.current = setInterval(poll, POLL_INTERVAL);
        return () => clearInterval(pollRef.current);
    }, [isAuthenticated, isSupport, poll]);

    // Browser Notification Permission beim ersten Laden anfragen
    useEffect(() => {
        if (isAuthenticated && isSupport() && 'Notification' in window && Notification.permission === 'default') {
            // Kurz warten damit die UI zuerst lädt
            setTimeout(requestPermission, 3000);
        }
    }, [isAuthenticated, isSupport, requestPermission]);

    const addTestNotification = useCallback(() => {
        const notif = {
            id: `test-${Date.now()}`,
            type: 'new_ticket',
            ticketId: 9999,
            ticketNumber: 'TKT-TEST',
            title: 'Neues Ticket: Test-Benachrichtigung',
            body: '🔴 Kritisch · Hardware',
            createdAt: new Date().toISOString(),
            read: false,
            critical: true,
        };
        setNotifications(prev => [notif, ...prev].slice(0, 50));
        sendBrowserNotif('📋 TKT-TEST: Test-Benachrichtigung', '🔴 Kritisch · Hardware', 'test-notif');
    }, [sendBrowserNotif]);

    const unreadCount = notifications.filter(n => !n.read).length;

    return (
        <NotificationContext.Provider value={{
            notifications,
            unreadCount,
            markAllRead,
            markRead,
            permission,
            requestPermission,
            pollNow: poll,
            addTestNotification,
        }}>
            {children}
        </NotificationContext.Provider>
    );
};
