105 lines
4.8 KiB
TypeScript
105 lines
4.8 KiB
TypeScript
import Link from 'next/link'
|
||
import { supabaseAdmin, listAuthUsers } from '@/lib/supabaseAdmin'
|
||
|
||
interface ProfileRow {
|
||
id: string
|
||
full_name: string | null
|
||
bar_association_no: string | null
|
||
bar_name: string | null
|
||
license_status: string | null
|
||
license_expires_at: string | null
|
||
trial_end_date: string | null
|
||
org_id: string | null
|
||
created_at: string
|
||
}
|
||
|
||
function statusBadge(status: string | null) {
|
||
const map: Record<string, string> = {
|
||
active: 'bg-green-50 text-green-700 border-green-200 dark:bg-green-950/40 dark:text-green-400 dark:border-green-900',
|
||
trial: 'bg-amber-50 text-amber-700 border-amber-200 dark:bg-amber-950/40 dark:text-amber-400 dark:border-amber-900',
|
||
expired: 'bg-red-50 text-red-700 border-red-200 dark:bg-red-950/40 dark:text-red-400 dark:border-red-900',
|
||
}
|
||
const cls = map[status || ''] || 'bg-gray-50 text-gray-600 border-gray-200 dark:bg-gray-900 dark:text-gray-400 dark:border-gray-800'
|
||
return (
|
||
<span className={`inline-flex items-center px-2 py-0.5 rounded-full text-xs font-medium border ${cls}`}>
|
||
{status || 'bilinmiyor'}
|
||
</span>
|
||
)
|
||
}
|
||
|
||
function formatDate(iso: string | null) {
|
||
if (!iso) return '—'
|
||
return new Date(iso).toLocaleDateString('tr-TR', { day: 'numeric', month: 'short', year: 'numeric' })
|
||
}
|
||
|
||
export default async function UsersPage({ searchParams }: { searchParams: Promise<{ deleted?: string }> }) {
|
||
const { deleted } = await searchParams
|
||
const [{ data: profiles }, authUsers] = await Promise.all([
|
||
supabaseAdmin
|
||
.from('profiles')
|
||
.select('id, full_name, bar_association_no, bar_name, license_status, license_expires_at, trial_end_date, org_id, created_at')
|
||
.order('created_at', { ascending: false }),
|
||
listAuthUsers(),
|
||
])
|
||
|
||
const rows = (profiles as ProfileRow[] | null) || []
|
||
|
||
return (
|
||
<div className="space-y-6">
|
||
{deleted && (
|
||
<div className="rounded-md bg-green-50 dark:bg-green-950/40 border border-green-200 dark:border-green-900 px-4 py-3 text-sm text-green-700 dark:text-green-400">
|
||
Kullanıcı silindi.
|
||
</div>
|
||
)}
|
||
<div>
|
||
<h2 className="text-2xl font-bold tracking-tight text-gray-900 dark:text-white">Kullanıcılar</h2>
|
||
<p className="text-gray-500 dark:text-gray-400 mt-2">Toplam {rows.length} kullanıcı.</p>
|
||
</div>
|
||
|
||
<div className="rounded-lg bg-white dark:bg-gray-950 border border-gray-200 dark:border-gray-800 shadow-sm overflow-hidden">
|
||
<div className="overflow-x-auto">
|
||
<table className="min-w-full divide-y divide-gray-200 dark:divide-gray-800">
|
||
<thead className="bg-gray-50 dark:bg-gray-900">
|
||
<tr>
|
||
{['Kullanıcı', 'Baro', 'Durum', 'Bitiş Tarihi', 'Kayıt', ''].map((h) => (
|
||
<th key={h} className="px-4 py-3 text-left text-xs font-medium text-gray-500 dark:text-gray-400 uppercase tracking-wider">{h}</th>
|
||
))}
|
||
</tr>
|
||
</thead>
|
||
<tbody className="divide-y divide-gray-100 dark:divide-gray-800">
|
||
{rows.map((p) => {
|
||
const authUser = authUsers.get(p.id)
|
||
const expiryDate = p.license_status === 'trial' ? p.trial_end_date : p.license_expires_at
|
||
return (
|
||
<tr key={p.id} className="hover:bg-gray-50 dark:hover:bg-gray-900/50">
|
||
<td className="px-4 py-3 whitespace-nowrap">
|
||
<div className="text-sm font-medium text-gray-900 dark:text-white">{p.full_name || '(isimsiz)'}</div>
|
||
<div className="text-xs text-gray-500">{authUser?.email || p.id}</div>
|
||
</td>
|
||
<td className="px-4 py-3 whitespace-nowrap text-sm text-gray-600 dark:text-gray-400">
|
||
{p.bar_name || '—'}{p.bar_association_no ? ` · ${p.bar_association_no}` : ''}
|
||
</td>
|
||
<td className="px-4 py-3 whitespace-nowrap">{statusBadge(p.license_status)}</td>
|
||
<td className="px-4 py-3 whitespace-nowrap text-sm text-gray-600 dark:text-gray-400">{formatDate(expiryDate)}</td>
|
||
<td className="px-4 py-3 whitespace-nowrap text-sm text-gray-500">{formatDate(p.created_at)}</td>
|
||
<td className="px-4 py-3 whitespace-nowrap text-right text-sm">
|
||
<Link href={`/admin/users/${p.id}`} className="text-indigo-600 dark:text-indigo-400 hover:underline">
|
||
Düzenle
|
||
</Link>
|
||
</td>
|
||
</tr>
|
||
)
|
||
})}
|
||
{rows.length === 0 && (
|
||
<tr>
|
||
<td colSpan={6} className="px-4 py-8 text-center text-sm text-gray-500">Henüz kullanıcı yok.</td>
|
||
</tr>
|
||
)}
|
||
</tbody>
|
||
</table>
|
||
</div>
|
||
</div>
|
||
</div>
|
||
)
|
||
}
|