import React, { useState, useEffect } from 'react';
import { io, Socket } from 'socket.io-client';
import type { ServiceConfig, ProviderConfig, Environment, AuditLogEntry } from '../../types';

const AdminPanel: React.FC = () => {
  const [isAuthenticated, setIsAuthenticated] = useState(false);
  const [adminToken, setAdminToken] = useState<string | null>(
    localStorage.getItem('adminToken')
  );
  const [activeTab, setActiveTab] = useState<'services' | 'providers' | 'environments' | 'audit'>('services');

  const [loginForm, setLoginForm] = useState({ username: '', password: '' });
  const [services, setServices] = useState<ServiceConfig[]>([]);
  const [providers, setProviders] = useState<ProviderConfig[]>([]);
  const [environments, setEnvironments] = useState<Environment[]>([]);
  const [auditLogs, setAuditLogs] = useState<AuditLogEntry[]>([]);
  const [socket, setSocket] = useState<Socket | null>(null);

  useEffect(() => {
    setIsAuthenticated(!!adminToken);
    if (adminToken) {
      loadData();
      
      // Initialize WebSocket connection for real-time updates
      const ws = io(window.location.origin);
      ws.on('connect', () => {
        console.log('Connected to WebSocket server');
        ws.emit('join-admin');
      });
      
      ws.on('admin-update', (data: { type: string; data: any; timestamp: string }) => {
        console.log('Admin update received:', data);
        
        // Refresh relevant data based on update type
        if (data.type === 'service-updated') {
          loadServices();
          loadAuditLogs();
        } else if (data.type === 'provider-updated') {
          loadProviders();
          loadAuditLogs();
        } else if (data.type === 'environment-updated') {
          loadEnvironments();
          loadAuditLogs();
        }
      });
      
      ws.on('disconnect', () => {
        console.log('Disconnected from WebSocket server');
      });
      
      setSocket(ws);
      
      return () => {
        ws.disconnect();
      };
    }
  }, [adminToken]);

  const getAuthHeaders = () => ({
    'Content-Type': 'application/json',
    'X-Admin-Token': adminToken || '',
  });

  const handleLogin = async (e: React.FormEvent) => {
    e.preventDefault();
    try {
      const response = await fetch('/api/admin/login', {
        method: 'POST',
        headers: { 'Content-Type': 'application/json' },
        body: JSON.stringify(loginForm),
      });

      if (response.ok) {
        const data = await response.json();
        setAdminToken(data.token);
        localStorage.setItem('adminToken', data.token);
        setIsAuthenticated(true);
        loadData();
      } else {
        alert('Invalid credentials');
      }
    } catch (error) {
      console.error('Login error:', error);
      alert('Login failed');
    }
  };

  const handleLogout = () => {
    setAdminToken(null);
    localStorage.removeItem('adminToken');
    setIsAuthenticated(false);
  };

  const loadServices = async () => {
    try {
      const response = await fetch('/api/admin/services', { headers: getAuthHeaders() });
      if (response.ok) {
        setServices(await response.json());
      }
    } catch (error) {
      console.error('Failed to load services:', error);
    }
  };

  const loadProviders = async () => {
    try {
      const response = await fetch('/api/admin/providers', { headers: getAuthHeaders() });
      if (response.ok) {
        setProviders(await response.json());
      }
    } catch (error) {
      console.error('Failed to load providers:', error);
    }
  };

  const loadEnvironments = async () => {
    try {
      const response = await fetch('/api/environments');
      if (response.ok) {
        setEnvironments(await response.json());
      }
    } catch (error) {
      console.error('Failed to load environments:', error);
    }
  };

  const loadAuditLogs = async () => {
    try {
      const response = await fetch('/api/admin/audit-logs?limit=100', { headers: getAuthHeaders() });
      if (response.ok) {
        setAuditLogs(await response.json());
      }
    } catch (error) {
      console.error('Failed to load audit logs:', error);
    }
  };

  const loadData = () => {
    loadServices();
    loadProviders();
    loadEnvironments();
    loadAuditLogs();
  };

  const toggleService = async (serviceName: string, enabled: boolean) => {
    try {
      const response = await fetch(`/api/admin/services/${serviceName}`, {
        method: 'PUT',
        headers: getAuthHeaders(),
        body: JSON.stringify({ enabled }),
      });

      if (response.ok) {
        await loadServices();
        await loadAuditLogs();
      } else {
        alert('Failed to update service');
      }
    } catch (error) {
      console.error('Failed to toggle service:', error);
      alert('Failed to update service');
    }
  };

  const toggleProvider = async (providerName: string, enabled: boolean) => {
    try {
      const response = await fetch(`/api/admin/providers/${providerName}`, {
        method: 'PUT',
        headers: getAuthHeaders(),
        body: JSON.stringify({ enabled }),
      });

      if (response.ok) {
        await loadProviders();
        await loadAuditLogs();
      } else {
        alert('Failed to update provider');
      }
    } catch (error) {
      console.error('Failed to toggle provider:', error);
      alert('Failed to update provider');
    }
  };

  const toggleEnvironment = async (envName: string, enabled: boolean) => {
    try {
      const response = await fetch(`/api/admin/environments/${envName}/toggle`, {
        method: 'PUT',
        headers: getAuthHeaders(),
        body: JSON.stringify({ enabled }),
      });

      if (response.ok) {
        await loadEnvironments();
        await loadAuditLogs();
      } else {
        alert('Failed to update environment');
      }
    } catch (error) {
      console.error('Failed to toggle environment:', error);
      alert('Failed to update environment');
    }
  };

  const formatDate = (dateString: string): string => {
    return new Date(dateString).toLocaleString();
  };

  if (!isAuthenticated) {
    return (
      <div className="max-w-md mx-auto card">
        <h2 className="text-2xl font-bold mb-4">Admin Login</h2>
        <form onSubmit={handleLogin} className="space-y-4">
          <div>
            <label htmlFor="admin-username" className="block text-sm font-medium text-gray-700 mb-1">Username</label>
            <input
              id="admin-username"
              name="username"
              type="text"
              value={loginForm.username}
              onChange={(e) => setLoginForm({ ...loginForm, username: e.target.value })}
              required
              className="w-full px-3 py-2 border border-gray-300 rounded-lg focus:ring-2 focus:ring-primary-500"
              placeholder="admin"
              aria-label="Username"
            />
          </div>
          <div>
            <label htmlFor="admin-password" className="block text-sm font-medium text-gray-700 mb-1">Password</label>
            <input
              id="admin-password"
              name="password"
              type="password"
              value={loginForm.password}
              onChange={(e) => setLoginForm({ ...loginForm, password: e.target.value })}
              required
              className="w-full px-3 py-2 border border-gray-300 rounded-lg focus:ring-2 focus:ring-primary-500"
              placeholder="Enter password"
              aria-label="Password"
            />
          </div>
          <button type="submit" className="btn btn-primary w-full">Login</button>
        </form>
      </div>
    );
  }

  return (
    <div className="admin-panel">
      <div className="mb-8">
        <h1 className="text-3xl font-bold mb-2">Admin Panel</h1>
        <p className="text-gray-600">Manage services, providers, and environments</p>
      </div>

      {/* Tabs */}
      <div className="border-b border-gray-200">
        <nav className="flex space-x-8">
          <button
            onClick={() => setActiveTab('services')}
            className={`py-4 px-1 border-b-2 font-medium text-sm ${
              activeTab === 'services'
                ? 'border-primary-500 text-primary-600'
                : 'border-transparent text-gray-500 hover:text-gray-700 hover:border-gray-300'
            }`}
          >
            Services
          </button>
          <button
            onClick={() => setActiveTab('providers')}
            className={`py-4 px-1 border-b-2 font-medium text-sm ${
              activeTab === 'providers'
                ? 'border-primary-500 text-primary-600'
                : 'border-transparent text-gray-500 hover:text-gray-700 hover:border-gray-300'
            }`}
          >
            Providers
          </button>
          <button
            onClick={() => setActiveTab('environments')}
            className={`py-4 px-1 border-b-2 font-medium text-sm ${
              activeTab === 'environments'
                ? 'border-primary-500 text-primary-600'
                : 'border-transparent text-gray-500 hover:text-gray-700 hover:border-gray-300'
            }`}
          >
            Environments
          </button>
          <button
            onClick={() => setActiveTab('audit')}
            className={`py-4 px-1 border-b-2 font-medium text-sm ${
              activeTab === 'audit'
                ? 'border-primary-500 text-primary-600'
                : 'border-transparent text-gray-500 hover:text-gray-700 hover:border-gray-300'
            }`}
          >
            Audit Logs
          </button>
        </nav>
      </div>

      {/* Services Tab */}
      {activeTab === 'services' && (
        <div className="space-y-4 mt-6">
          <div className="flex justify-between items-center">
            <h2 className="text-2xl font-bold">Services</h2>
            <button onClick={loadServices} className="btn btn-secondary">
              <i className="fas fa-sync-alt mr-2"></i>Refresh
            </button>
          </div>
          <div className="grid grid-cols-1 md:grid-cols-2 lg:grid-cols-3 gap-4">
            {services.map((service) => (
              <div key={service.service_name} className="card">
                <div className="flex justify-between items-start mb-4">
                  <h3 className="text-lg font-semibold">{service.service_name}</h3>
                  <label className="relative inline-flex items-center cursor-pointer">
                    <input
                      type="checkbox"
                      checked={service.enabled}
                      onChange={(e) => toggleService(service.service_name, e.target.checked)}
                      className="sr-only peer"
                    />
                    <div className="w-11 h-6 bg-gray-200 peer-focus:outline-none peer-focus:ring-4 peer-focus:ring-primary-300 rounded-full peer peer-checked:after:translate-x-full peer-checked:after:border-white after:content-[''] after:absolute after:top-[2px] after:left-[2px] after:bg-white after:border-gray-300 after:border after:rounded-full after:h-5 after:w-5 after:transition-all peer-checked:bg-primary-600"></div>
                  </label>
                </div>
                <div className="text-sm text-gray-500">
                  <div>Updated: {formatDate(service.updated_at)}</div>
                  {service.updated_by && <div>By: {service.updated_by}</div>}
                </div>
              </div>
            ))}
          </div>
        </div>
      )}

      {/* Providers Tab */}
      {activeTab === 'providers' && (
        <div className="space-y-4 mt-6">
          <div className="flex justify-between items-center">
            <h2 className="text-2xl font-bold">Providers</h2>
            <button onClick={loadProviders} className="btn btn-secondary">
              <i className="fas fa-sync-alt mr-2"></i>Refresh
            </button>
          </div>
          <div className="grid grid-cols-1 md:grid-cols-2 lg:grid-cols-3 gap-4">
            {providers.map((provider) => (
              <div key={provider.provider_name} className="card">
                <div className="flex justify-between items-start mb-4">
                  <h3 className="text-lg font-semibold capitalize">{provider.provider_name}</h3>
                  <label className="relative inline-flex items-center cursor-pointer">
                    <input
                      type="checkbox"
                      checked={provider.enabled}
                      onChange={(e) => toggleProvider(provider.provider_name, e.target.checked)}
                      className="sr-only peer"
                    />
                    <div className="w-11 h-6 bg-gray-200 peer-focus:outline-none peer-focus:ring-4 peer-focus:ring-primary-300 rounded-full peer peer-checked:after:translate-x-full peer-checked:after:border-white after:content-[''] after:absolute after:top-[2px] after:left-[2px] after:bg-white after:border-gray-300 after:border after:rounded-full after:h-5 after:w-5 after:transition-all peer-checked:bg-primary-600"></div>
                  </label>
                </div>
                <div className="text-sm text-gray-500">
                  <div>Updated: {formatDate(provider.updated_at)}</div>
                  {provider.updated_by && <div>By: {provider.updated_by}</div>}
                </div>
              </div>
            ))}
          </div>
        </div>
      )}

      {/* Environments Tab */}
      {activeTab === 'environments' && (
        <div className="space-y-4 mt-6">
          <div className="flex justify-between items-center">
            <h2 className="text-2xl font-bold">Environments</h2>
            <button onClick={loadEnvironments} className="btn btn-secondary">
              <i className="fas fa-sync-alt mr-2"></i>Refresh
            </button>
          </div>
          <div className="grid grid-cols-1 md:grid-cols-2 lg:grid-cols-3 gap-4">
            {environments.map((env) => (
              <div key={env.name} className="card">
                <div className="flex justify-between items-start mb-4">
                  <div>
                    <h3 className="text-lg font-semibold">{env.name}</h3>
                    <div className="text-sm text-gray-500">
                      {env.provider} • {env.region}
                    </div>
                  </div>
                  <label className="relative inline-flex items-center cursor-pointer">
                    <input
                      type="checkbox"
                      checked={env.enabled}
                      onChange={(e) => toggleEnvironment(env.name, e.target.checked)}
                      className="sr-only peer"
                    />
                    <div className="w-11 h-6 bg-gray-200 peer-focus:outline-none peer-focus:ring-4 peer-focus:ring-primary-300 rounded-full peer peer-checked:after:translate-x-full peer-checked:after:border-white after:content-[''] after:absolute after:top-[2px] after:left-[2px] after:bg-white after:border-gray-300 after:border after:rounded-full after:h-5 after:w-5 after:transition-all peer-checked:bg-primary-600"></div>
                  </label>
                </div>
                <div className="text-sm">
                  <span className={env.enabled ? 'text-green-600' : 'text-gray-400'}>
                    {env.enabled ? 'Enabled' : 'Disabled'}
                  </span>
                </div>
              </div>
            ))}
          </div>
        </div>
      )}

      {/* Audit Logs Tab */}
      {activeTab === 'audit' && (
        <div className="space-y-4 mt-6">
          <div className="flex justify-between items-center">
            <h2 className="text-2xl font-bold">Audit Logs</h2>
            <button onClick={loadAuditLogs} className="btn btn-secondary">
              <i className="fas fa-sync-alt mr-2"></i>Refresh
            </button>
          </div>
          <div className="card overflow-x-auto">
            <table className="min-w-full divide-y divide-gray-200">
              <thead className="bg-gray-50">
                <tr>
                  <th className="px-6 py-3 text-left text-xs font-medium text-gray-500 uppercase tracking-wider">Timestamp</th>
                  <th className="px-6 py-3 text-left text-xs font-medium text-gray-500 uppercase tracking-wider">User</th>
                  <th className="px-6 py-3 text-left text-xs font-medium text-gray-500 uppercase tracking-wider">Action</th>
                  <th className="px-6 py-3 text-left text-xs font-medium text-gray-500 uppercase tracking-wider">Resource</th>
                  <th className="px-6 py-3 text-left text-xs font-medium text-gray-500 uppercase tracking-wider">IP Address</th>
                </tr>
              </thead>
              <tbody className="bg-white divide-y divide-gray-200">
                {auditLogs.map((log) => (
                  <tr key={log.id}>
                    <td className="px-6 py-4 whitespace-nowrap text-sm text-gray-500">{formatDate(log.timestamp)}</td>
                    <td className="px-6 py-4 whitespace-nowrap text-sm font-medium text-gray-900">{log.admin_user}</td>
                    <td className="px-6 py-4 whitespace-nowrap text-sm text-gray-500">{log.action}</td>
                    <td className="px-6 py-4 whitespace-nowrap text-sm text-gray-500">
                      {log.resource_type}{log.resource_id ? `: ${log.resource_id}` : ''}
                    </td>
                    <td className="px-6 py-4 whitespace-nowrap text-sm text-gray-500">{log.ip_address}</td>
                  </tr>
                ))}
              </tbody>
            </table>
          </div>
        </div>
      )}

      {/* Logout Button */}
      <div className="flex justify-end mt-8">
        <button onClick={handleLogout} className="btn btn-secondary">
          <i className="fas fa-sign-out-alt mr-2"></i>Logout
        </button>
      </div>
    </div>
  );
};

export default AdminPanel;

