| Server IP : 54.37.205.81 / Your IP : 216.73.216.76 Web Server : nginx/1.22.1 System : Linux vps-249481fa 6.1.0-50-cloud-amd64 #1 SMP PREEMPT_DYNAMIC Debian 6.1.176-1 (2026-07-02) x86_64 User : debian ( 1000) PHP Version : 8.2.32 Disable Function : NONE MySQL : OFF | cURL : ON | WGET : ON | Perl : ON | Python : OFF | Sudo : ON | Pkexec : OFF Directory : /var/www/app.copyrightchain.it/copyrightchain_app/components/ |
Upload File : |
import React, { useState, useMemo } from 'react';
import { Lock, User, Shield, ArrowRight, Loader2, AlertCircle } from 'lucide-react';
import { Language } from '../types';
import { translations } from '../translations';
import { useNotification } from '../App';
import { useAuth } from '../context/AuthContext';
interface AdminLoginProps { lang: Language; }
const AdminLogin: React.FC<AdminLoginProps> = ({ lang }) => {
const t = useMemo(() => translations[lang], [lang]);
const { notify } = useNotification();
const { login } = useAuth();
const [username, setUsername] = useState('');
const [password, setPassword] = useState('');
const [isLoading, setIsLoading] = useState(false);
const [error, setError] = useState(false);
const handleSubmit = async (e: React.FormEvent) => {
e.preventDefault();
setIsLoading(true);
setError(false);
try {
await login(username, password);
notify(lang === 'it' ? "Accesso autorizzato" : "Access authorized", "success");
} catch (e: any) {
setError(true);
notify(e?.message || t.invalidCredentials, "error");
} finally {
setIsLoading(false);
}
};
return (
<div className="min-h-[70vh] flex items-center justify-center p-6 animate-in fade-in duration-700">
<div className="w-full max-w-md bg-white rounded-[3.5rem] shadow-2xl border border-slate-100 overflow-hidden relative">
<div className="absolute top-0 left-0 w-full h-1.5 bg-slate-900"></div>
<div className="absolute top-0 right-0 p-10 opacity-[0.02] pointer-events-none"><Lock size={150} /></div>
<div className="p-10 md:p-12">
<div className="flex flex-col items-center text-center mb-10">
<div className="bg-slate-900 text-white p-4 rounded-2xl shadow-xl mb-6"><Shield size={32} /></div>
<h2 className="text-3xl font-black text-slate-900 uppercase tracking-tight leading-none">{t.adminLoginTitle}</h2>
<p className="text-slate-500 font-medium text-sm mt-3">{t.adminLoginDesc}</p>
</div>
<form onSubmit={handleSubmit} className="space-y-6">
<div className="space-y-2">
<label className="text-[10px] font-black text-slate-400 uppercase tracking-widest ml-1">{t.username}</label>
<div className="relative">
<input
required
type="text"
value={username}
onChange={(e) => setUsername(e.target.value)}
className={`w-full pl-12 pr-6 py-4 bg-slate-50 border rounded-2xl font-bold text-sm outline-none transition-all focus:ring-4 focus:ring-slate-900/5 ${error ? 'border-red-300' : 'border-slate-100'}`}
placeholder="admin"
/>
<div className="absolute left-4 top-1/2 -translate-y-1/2 text-slate-400"><User size={18} /></div>
</div>
</div>
<div className="space-y-2">
<label className="text-[10px] font-black text-slate-400 uppercase tracking-widest ml-1">{t.password}</label>
<div className="relative">
<input
required
type="password"
value={password}
onChange={(e) => setPassword(e.target.value)}
className={`w-full pl-12 pr-6 py-4 bg-slate-50 border rounded-2xl font-bold text-sm outline-none transition-all focus:ring-4 focus:ring-slate-900/5 ${error ? 'border-red-300' : 'border-slate-100'}`}
placeholder="••••••••"
/>
<div className="absolute left-4 top-1/2 -translate-y-1/2 text-slate-400"><Lock size={18} /></div>
</div>
</div>
{error && (
<div className="flex items-center gap-2 text-red-600 bg-red-50 p-4 rounded-xl border border-red-100 animate-in shake duration-300">
<AlertCircle size={16} />
<span className="text-[10px] font-black uppercase tracking-widest">{t.invalidCredentials}</span>
</div>
)}
<button
type="submit"
disabled={isLoading}
className="w-full py-5 bg-slate-900 text-white rounded-2xl font-black uppercase tracking-[0.2em] text-[10px] shadow-2xl flex items-center justify-center gap-3 hover:bg-slate-800 transition-all disabled:opacity-50"
>
{isLoading ? <Loader2 size={18} className="animate-spin" /> : <><Lock size={18} /> {t.loginAction}</>}
</button>
</form>
<div className="mt-10 pt-8 border-t border-slate-50 flex items-center justify-center gap-2">
<span className="w-1.5 h-1.5 rounded-full bg-emerald-500 animate-pulse"></span>
<span className="text-[9px] font-black text-slate-400 uppercase tracking-widest">CopyrightChain Security Protocol v4.0</span>
</div>
</div>
</div>
</div>
);
};
export default AdminLogin;