T.ME/BIBIL_0DAY
CasperSecurity


Server : Apache/2
System : Linux server-15-235-50-60 5.15.0-164-generic #174-Ubuntu SMP Fri Nov 14 20:25:16 UTC 2025 x86_64
User : gositeme ( 1004)
PHP Version : 8.2.29
Disable Function : exec,system,passthru,shell_exec,proc_close,proc_open,dl,popen,show_source,posix_kill,posix_mkfifo,posix_getpwuid,posix_setpgid,posix_setsid,posix_setuid,posix_setgid,posix_seteuid,posix_setegid,posix_uname
Directory :  /home/gositeme/domains/lavocat.ca/private_html/src/pages/admin/

Upload File :
current_dir [ Writeable ] document_root [ Writeable ]

 

Current File : /home/gositeme/domains/lavocat.ca/private_html/src/pages/admin/case-showcase-manager.tsx
import React, { useState, useEffect } from 'react';
import { useSession } from 'next-auth/react';
import { useRouter } from 'next/router';
import Head from 'next/head';
import LayoutWithSidebar from '../../components/LayoutWithSidebar';
import { 
  Plus, 
  Edit, 
  Eye, 
  ExternalLink, 
  Users, 
  Calendar, 
  DollarSign,
  Target,
  CheckCircle,
  Clock,
  AlertTriangle,
  Star,
  TrendingUp,
  FileText,
  Building,
  Globe,
  Shield,
  Heart,
  Zap,
  Award
} from 'lucide-react';
import Link from 'next/link';

const CaseShowcaseManager: React.FC = () => {
  const { data: session } = useSession();
  const router = useRouter();
  const [cases, setCases] = useState<any[]>([]);
  const [loading, setLoading] = useState(true);
  const [filter, setFilter] = useState('all');

  useEffect(() => {
    if (session) {
      fetchCases();
    }
  }, [session]);

  const fetchCases = async () => {
    try {
      const response = await fetch('/api/admin/cases');
      if (response.ok) {
        const data = await response.json();
        setCases(data.cases || []);
      }
    } catch (error) {
      console.error('Error fetching cases:', error);
    } finally {
      setLoading(false);
    }
  };

  const getStatusIcon = (status: string) => {
    switch (status?.toLowerCase()) {
      case 'active': return <CheckCircle className="h-5 w-5 text-green-500" />;
      case 'pending': return <Clock className="h-5 w-5 text-yellow-500" />;
      case 'closed': return <AlertTriangle className="h-5 w-5 text-gray-500" />;
      default: return <Clock className="h-5 w-5 text-gray-400" />;
    }
  };

  const getCategoryIcon = (category: string) => {
    switch (category?.toLowerCase()) {
      case 'human_rights': return 'πŸ›οΈ';
      case 'criminal': return 'βš–οΈ';
      case 'civil': return 'πŸ“‹';
      case 'family': return 'πŸ‘¨β€πŸ‘©β€πŸ‘§β€πŸ‘¦';
      case 'corporate': return '🏒';
      case 'class_action': return 'πŸ‘₯';
      case 'immigration': return '🌍';
      case 'employment': return 'πŸ’Ό';
      default: return 'πŸ“„';
    }
  };

  const getPriorityColor = (priority: string) => {
    switch (priority?.toLowerCase()) {
      case 'high': return 'bg-red-100 text-red-800 border-red-200';
      case 'medium': return 'bg-yellow-100 text-yellow-800 border-yellow-200';
      case 'low': return 'bg-green-100 text-green-800 border-green-200';
      default: return 'bg-gray-100 text-gray-800 border-gray-200';
    }
  };

  const filteredCases = cases.filter(case_ => {
    if (filter === 'all') return true;
    if (filter === 'public' && case_.isPublic) return true;
    if (filter === 'active' && case_.status === 'active') return true;
    if (filter === 'pending' && case_.status === 'pending') return true;
    return false;
  });

  if (!session) {
    return (
      <LayoutWithSidebar>
        <div className="min-h-screen bg-gray-50 flex items-center justify-center">
          <div className="text-center">
            <h1 className="text-4xl font-bold text-gray-900 mb-4">Access Denied</h1>
            <p className="text-gray-600 mb-8">Please log in to access this page.</p>
            <button
              onClick={() => router.push('/auth/signin')}
              className="inline-flex items-center px-4 py-2 bg-blue-600 text-white rounded-lg hover:bg-blue-700 transition-colors"
            >
              Sign In
            </button>
          </div>
        </div>
      </LayoutWithSidebar>
    );
  }

  return (
    <>
      <Head>
        <title>Case Showcase Manager | LibertΓ© MΓͺme en Prison</title>
        <meta name="description" content="Manage beautiful case profile presentations" />
      </Head>
      
      <LayoutWithSidebar>
        <div className="max-w-7xl mx-auto px-4 sm:px-6 lg:px-8 py-8">
          {/* Header */}
          <div className="mb-8">
            <div className="flex items-center justify-between">
              <div>
                <h1 className="text-3xl font-bold text-gray-900">Case Showcase Manager</h1>
                <p className="text-gray-600 mt-2">
                  Create and manage beautiful case profile presentations for your clients
                </p>
              </div>
              <Link
                href="/admin/cases/new"
                className="inline-flex items-center px-4 py-2 bg-blue-600 text-white rounded-lg hover:bg-blue-700 transition-colors"
              >
                <Plus className="h-4 w-4 mr-2" />
                Create New Case
              </Link>
            </div>
          </div>

          {/* Stats Cards */}
          <div className="grid grid-cols-1 md:grid-cols-4 gap-6 mb-8">
            <div className="bg-white rounded-xl shadow-sm border border-gray-200 p-6">
              <div className="flex items-center">
                <div className="w-12 h-12 bg-blue-100 rounded-lg flex items-center justify-center">
                  <FileText className="h-6 w-6 text-blue-600" />
                </div>
                <div className="ml-4">
                  <p className="text-sm font-medium text-gray-600">Total Cases</p>
                  <p className="text-2xl font-bold text-gray-900">{cases.length}</p>
                </div>
              </div>
            </div>
            
            <div className="bg-white rounded-xl shadow-sm border border-gray-200 p-6">
              <div className="flex items-center">
                <div className="w-12 h-12 bg-green-100 rounded-lg flex items-center justify-center">
                  <CheckCircle className="h-6 w-6 text-green-600" />
                </div>
                <div className="ml-4">
                  <p className="text-sm font-medium text-gray-600">Public Cases</p>
                  <p className="text-2xl font-bold text-gray-900">
                    {cases.filter(c => c.isPublic).length}
                  </p>
                </div>
              </div>
            </div>
            
            <div className="bg-white rounded-xl shadow-sm border border-gray-200 p-6">
              <div className="flex items-center">
                <div className="w-12 h-12 bg-yellow-100 rounded-lg flex items-center justify-center">
                  <Clock className="h-6 w-6 text-yellow-600" />
                </div>
                <div className="ml-4">
                  <p className="text-sm font-medium text-gray-600">Active Cases</p>
                  <p className="text-2xl font-bold text-gray-900">
                    {cases.filter(c => c.status === 'active').length}
                  </p>
                </div>
              </div>
            </div>
            
            <div className="bg-white rounded-xl shadow-sm border border-gray-200 p-6">
              <div className="flex items-center">
                <div className="w-12 h-12 bg-purple-100 rounded-lg flex items-center justify-center">
                  <Users className="h-6 w-6 text-purple-600" />
                </div>
                <div className="ml-4">
                  <p className="text-sm font-medium text-gray-600">Total Applications</p>
                  <p className="text-2xl font-bold text-gray-900">
                    {cases.reduce((sum, c) => sum + (c._count?.registrations || 0), 0)}
                  </p>
                </div>
              </div>
            </div>
          </div>

          {/* Filters */}
          <div className="mb-6">
            <div className="flex space-x-4">
              <button
                onClick={() => setFilter('all')}
                className={`px-4 py-2 rounded-lg font-medium transition-colors ${
                  filter === 'all' 
                    ? 'bg-blue-600 text-white' 
                    : 'bg-gray-100 text-gray-700 hover:bg-gray-200'
                }`}
              >
                All Cases
              </button>
              <button
                onClick={() => setFilter('public')}
                className={`px-4 py-2 rounded-lg font-medium transition-colors ${
                  filter === 'public' 
                    ? 'bg-blue-600 text-white' 
                    : 'bg-gray-100 text-gray-700 hover:bg-gray-200'
                }`}
              >
                Public Cases
              </button>
              <button
                onClick={() => setFilter('active')}
                className={`px-4 py-2 rounded-lg font-medium transition-colors ${
                  filter === 'active' 
                    ? 'bg-blue-600 text-white' 
                    : 'bg-gray-100 text-gray-700 hover:bg-gray-200'
                }`}
              >
                Active Cases
              </button>
              <button
                onClick={() => setFilter('pending')}
                className={`px-4 py-2 rounded-lg font-medium transition-colors ${
                  filter === 'pending' 
                    ? 'bg-blue-600 text-white' 
                    : 'bg-gray-100 text-gray-700 hover:bg-gray-200'
                }`}
              >
                Pending Cases
              </button>
            </div>
          </div>

          {/* Cases Grid */}
          {loading ? (
            <div className="flex items-center justify-center py-12">
              <div className="animate-spin rounded-full h-12 w-12 border-b-2 border-blue-600"></div>
            </div>
          ) : (
            <div className="grid grid-cols-1 md:grid-cols-2 lg:grid-cols-3 gap-6">
              {filteredCases.map((case_) => (
                <div key={case_.id} className="bg-white rounded-xl shadow-sm border border-gray-200 overflow-hidden hover:shadow-lg transition-shadow">
                  {/* Case Header */}
                  <div className="p-6">
                    <div className="flex items-start justify-between mb-4">
                      <div className="flex items-center gap-2">
                        <span className="text-2xl">{getCategoryIcon(case_.category)}</span>
                        {getStatusIcon(case_.status)}
                      </div>
                      <div className="flex items-center gap-2">
                        <span className={`px-2 py-1 rounded-full text-xs font-medium border ${getPriorityColor(case_.priority)}`}>
                          {case_.priority?.toUpperCase() || 'MEDIUM'}
                        </span>
                        {case_.isPublic && (
                          <span className="px-2 py-1 rounded-full text-xs font-medium bg-green-100 text-green-800 border border-green-200">
                            PUBLIC
                          </span>
                        )}
                      </div>
                    </div>
                    
                    <h3 className="font-bold text-gray-900 mb-2 line-clamp-2">{case_.title}</h3>
                    <p className="text-gray-600 text-sm mb-4 line-clamp-3">
                      {case_.publicSummary || case_.description || 'No description available'}
                    </p>
                    
                    {/* Case Stats */}
                    <div className="grid grid-cols-2 gap-4 mb-4">
                      <div className="text-center">
                        <p className="text-xs text-gray-500">Applications</p>
                        <p className="font-bold text-gray-900">{case_._count?.registrations || 0}</p>
                      </div>
                      <div className="text-center">
                        <p className="text-xs text-gray-500">Views</p>
                        <p className="font-bold text-gray-900">{case_.viewCount || 0}</p>
                      </div>
                    </div>
                    
                    {/* Case Details */}
                    <div className="space-y-2 text-sm text-gray-600">
                      {case_.caseNumber && (
                        <div className="flex items-center gap-2">
                          <FileText className="h-4 w-4" />
                          <span>{case_.caseNumber}</span>
                        </div>
                      )}
                      {case_.jurisdiction && (
                        <div className="flex items-center gap-2">
                          <Building className="h-4 w-4" />
                          <span>{case_.jurisdiction}</span>
                        </div>
                      )}
                      {case_.estimatedValue && (
                        <div className="flex items-center gap-2">
                          <DollarSign className="h-4 w-4" />
                          <span>${case_.estimatedValue.toLocaleString()}</span>
                        </div>
                      )}
                    </div>
                  </div>
                  
                  {/* Action Buttons */}
                  <div className="border-t border-gray-200 p-4 bg-gray-50">
                    <div className="flex items-center justify-between">
                      <div className="flex gap-2">
                        <Link
                          href={`/cases/${case_.id}/showcase`}
                          className="inline-flex items-center px-3 py-2 bg-blue-600 text-white text-sm rounded-lg hover:bg-blue-700 transition-colors"
                        >
                          <Eye className="h-4 w-4 mr-1" />
                          View Showcase
                        </Link>
                        <Link
                          href={`/admin/cases/${case_.id}`}
                          className="inline-flex items-center px-3 py-2 bg-gray-600 text-white text-sm rounded-lg hover:bg-gray-700 transition-colors"
                        >
                          <Edit className="h-4 w-4 mr-1" />
                          Edit
                        </Link>
                      </div>
                      <Link
                        href={`/cases/${case_.id}/showcase`}
                        target="_blank"
                        className="inline-flex items-center px-3 py-2 bg-white border border-gray-300 text-gray-700 text-sm rounded-lg hover:bg-gray-50 transition-colors"
                      >
                        <ExternalLink className="h-4 w-4 mr-1" />
                        Open
                      </Link>
                    </div>
                  </div>
                </div>
              ))}
            </div>
          )}

          {!loading && filteredCases.length === 0 && (
            <div className="text-center py-12">
              <div className="w-16 h-16 bg-gray-100 rounded-full flex items-center justify-center mx-auto mb-4">
                <FileText className="h-8 w-8 text-gray-400" />
              </div>
              <h3 className="text-lg font-medium text-gray-900 mb-2">No cases found</h3>
              <p className="text-gray-600 mb-6">
                {filter === 'all' 
                  ? "You haven't created any cases yet." 
                  : `No cases match the "${filter}" filter.`
                }
              </p>
              <Link
                href="/admin/cases/new"
                className="inline-flex items-center px-4 py-2 bg-blue-600 text-white rounded-lg hover:bg-blue-700 transition-colors"
              >
                <Plus className="h-4 w-4 mr-2" />
                Create Your First Case
              </Link>
            </div>
          )}
        </div>
      </LayoutWithSidebar>
    </>
  );
};

export default CaseShowcaseManager; 

CasperSecurity Mini