v1.0.3: PDF footer fix, arrow alignment, email verification workflow, account deletion
This commit is contained in:
@@ -91,6 +91,10 @@ export function Topbar({
|
||||
const [isLoadDialogOpen, setIsLoadDialogOpen] = useState(false)
|
||||
const [isHoseSettingsOpen, setIsHoseSettingsOpen] = useState(false)
|
||||
const [showPasswordDialog, setShowPasswordDialog] = useState(false)
|
||||
const [showDeleteAccountDialog, setShowDeleteAccountDialog] = useState(false)
|
||||
const [deleteAccountPw, setDeleteAccountPw] = useState('')
|
||||
const [deleteAccountLoading, setDeleteAccountLoading] = useState(false)
|
||||
const [deleteAccountError, setDeleteAccountError] = useState('')
|
||||
const [pwOld, setPwOld] = useState('')
|
||||
const [pwNew, setPwNew] = useState('')
|
||||
const [pwConfirm, setPwConfirm] = useState('')
|
||||
@@ -290,6 +294,13 @@ export function Topbar({
|
||||
Administration
|
||||
</DropdownMenuItem>
|
||||
)}
|
||||
<DropdownMenuItem
|
||||
onClick={() => { setShowDeleteAccountDialog(true); setDeleteAccountPw(''); setDeleteAccountError('') }}
|
||||
className="text-destructive focus:text-destructive"
|
||||
>
|
||||
<Trash2 className="w-4 h-4 mr-2" />
|
||||
Konto löschen
|
||||
</DropdownMenuItem>
|
||||
<DropdownMenuItem onClick={onLogout} className="text-destructive focus:text-destructive">
|
||||
<LogOut className="w-4 h-4 mr-2" />
|
||||
Abmelden
|
||||
@@ -539,6 +550,81 @@ export function Topbar({
|
||||
</div>
|
||||
</DialogContent>
|
||||
</Dialog>
|
||||
|
||||
{/* Delete Account Dialog */}
|
||||
<Dialog open={showDeleteAccountDialog} onOpenChange={setShowDeleteAccountDialog}>
|
||||
<DialogContent className="max-w-sm">
|
||||
<DialogHeader>
|
||||
<DialogTitle className="flex items-center gap-2 text-destructive">
|
||||
<AlertTriangle className="w-5 h-5" />
|
||||
Konto löschen
|
||||
</DialogTitle>
|
||||
</DialogHeader>
|
||||
<div className="space-y-4">
|
||||
<p className="text-sm text-muted-foreground">
|
||||
Ihr Konto wird unwiderruflich gelöscht. Ihre Projekte und Daten bleiben der Organisation erhalten,
|
||||
aber Ihr persönlicher Zugang wird entfernt.
|
||||
</p>
|
||||
{userRole === 'TENANT_ADMIN' && (
|
||||
<div className="bg-amber-50 dark:bg-amber-950/30 rounded-lg p-3 text-xs text-amber-800 dark:text-amber-300 border border-amber-200 dark:border-amber-800">
|
||||
<strong>Hinweis:</strong> Als einziger Administrator müssen Sie zuerst die Organisation unter Einstellungen löschen oder die Admin-Rolle übertragen.
|
||||
</div>
|
||||
)}
|
||||
<div className="space-y-1.5">
|
||||
<label className="text-sm font-medium">Passwort zur Bestätigung</label>
|
||||
<input
|
||||
type="password"
|
||||
value={deleteAccountPw}
|
||||
onChange={(e) => { setDeleteAccountPw(e.target.value); setDeleteAccountError('') }}
|
||||
placeholder="Ihr Passwort"
|
||||
className="w-full rounded-md border border-input bg-background px-3 py-2 text-sm"
|
||||
autoComplete="current-password"
|
||||
/>
|
||||
</div>
|
||||
{deleteAccountError && (
|
||||
<p className="text-sm text-destructive">{deleteAccountError}</p>
|
||||
)}
|
||||
<div className="flex gap-2 justify-end">
|
||||
<Button
|
||||
variant="outline"
|
||||
size="sm"
|
||||
onClick={() => setShowDeleteAccountDialog(false)}
|
||||
disabled={deleteAccountLoading}
|
||||
>
|
||||
Abbrechen
|
||||
</Button>
|
||||
<Button
|
||||
variant="destructive"
|
||||
size="sm"
|
||||
disabled={deleteAccountLoading || !deleteAccountPw}
|
||||
onClick={async () => {
|
||||
setDeleteAccountLoading(true)
|
||||
setDeleteAccountError('')
|
||||
try {
|
||||
const res = await fetch('/api/auth/delete-account', {
|
||||
method: 'POST',
|
||||
headers: { 'Content-Type': 'application/json' },
|
||||
body: JSON.stringify({ password: deleteAccountPw }),
|
||||
})
|
||||
const data = await res.json()
|
||||
if (res.ok) {
|
||||
window.location.href = '/'
|
||||
} else {
|
||||
setDeleteAccountError(data.error || 'Löschung fehlgeschlagen')
|
||||
}
|
||||
} catch {
|
||||
setDeleteAccountError('Verbindungsfehler')
|
||||
} finally {
|
||||
setDeleteAccountLoading(false)
|
||||
}
|
||||
}}
|
||||
>
|
||||
{deleteAccountLoading ? 'Wird gelöscht...' : 'Konto endgültig löschen'}
|
||||
</Button>
|
||||
</div>
|
||||
</div>
|
||||
</DialogContent>
|
||||
</Dialog>
|
||||
</header>
|
||||
)
|
||||
}
|
||||
|
||||
Reference in New Issue
Block a user