diff --git a/src/routes/admin/change-password/+page.svelte b/src/routes/admin/change-password/+page.svelte index ba7b824..a1505c2 100644 --- a/src/routes/admin/change-password/+page.svelte +++ b/src/routes/admin/change-password/+page.svelte @@ -1,82 +1,228 @@ + - -
-

🔐 Admin-Passwort ändern

- -
-
- - -
- -
- - -
- -
- - -
-
- + } + + function resetForm() { + oldPassword = ''; + newPassword = ''; + confirmPassword = ''; + message = ''; + error = ''; + } + + + + Passwort ändern - Admin + + +
+ + +
{#if error} -
{error}
+
+
+
+ + + +
+
+

Fehler

+

{error}

+
+
+
{/if} + {#if message} -
{message}
+
+
+
+ + + +
+
+

Erfolg

+

{message}

+
+
+
{/if} - -
- + + +
+
+
+
+ + + +
+
+

Passwort ändern

+

Aus Sicherheitsgründen sollten Sie Ihr Passwort regelmäßig ändern.

+
+
+ +
+
+ + +
+ +
+ + +
+ +
+ + +
+ +
+ + + +
+
+ + +
+
+
+ + + +
+
+

Sicherheitshinweise

+
+
    +
  • Verwenden Sie ein starkes Passwort mit mindestens 6 Zeichen
  • +
  • Kombinieren Sie Buchstaben, Zahlen und Sonderzeichen
  • +
  • Verwenden Sie dieses Passwort nicht für andere Dienste
  • +
  • Ändern Sie Ihr Passwort regelmäßig
  • +
+
+
+
+
+
-
\ No newline at end of file +
+
\ No newline at end of file diff --git a/src/routes/admin/dienststellen/+page.svelte b/src/routes/admin/dienststellen/+page.svelte index 60c13a8..2da1992 100644 --- a/src/routes/admin/dienststellen/+page.svelte +++ b/src/routes/admin/dienststellen/+page.svelte @@ -1,26 +1,49 @@ + - -
-

Dienststellen verwalten

- - -
- - - - -
+ await ladeDienststellen(); + } else { + const err = await res.json(); + fehlermeldung = err.error || 'Fehler beim Speichern'; + } + } catch (err) { + fehlermeldung = err instanceof Error ? err.message : 'Fehler beim Speichern'; + console.error(err); + } + } - - {#if fehlermeldung} -

{fehlermeldung}

- {/if} + async function loeschen(id: number) { + if (!confirm('Diese Dienststelle wirklich löschen?')) return; + + try { + const res = await fetch(`/api/admin/dienststellen?id=${id}`, { method: 'DELETE' }); + + if (!res.ok) { + const err = await res.json(); + fehlermeldung = err.error || 'Fehler beim Löschen'; + return; + } + + await ladeDienststellen(); + } catch (err) { + fehlermeldung = err instanceof Error ? err.message : 'Fehler beim Löschen'; + console.error(err); + } + } - -
-
- -
-
Dienststelle
-
Plätze
-
Aktionen
-
+ function resetForm() { + neuerName = ''; + neuePlaetze = 0; + bearbeiteId = null; + } - - {#each dienststellen as d} -
-
{d.name}
-
{d.plaetze}
-
- - + onMount(ladeDienststellen); + + + + Dienststellen verwalten - Admin + + +
+ + +
+ {#if fehlermeldung} +
+
+
+ + + +
+
+

Fehler

+

{fehlermeldung}

- {/each} +
+ {/if} + + +
+

+ {bearbeiteId !== null ? 'Dienststelle bearbeiten' : 'Neue Dienststelle hinzufügen'} +

+ +
+
+ + +
+ +
+ + +
+ +
+ + +
+
-
- -
- -
-
- - - + {#if isLoading} +
+
+ Lade Dienststellen... +
+ {:else if dienststellen.length === 0} +
+ + + +

Keine Dienststellen

+

Erstellen Sie Ihre erste Dienststelle über das Formular oben.

+
+ {:else} +
+
+

Alle Dienststellen

+
+ +
+ + + + + + + + + + {#each dienststellen as d} + + + + + + {/each} + +
+ Dienststelle + + Plätze + + Aktionen +
+ {d.name} + + {d.plaetze} + + + +
+
+
+ {/if} + +
\ No newline at end of file diff --git a/src/routes/admin/zeitraeume/+page.svelte b/src/routes/admin/zeitraeume/+page.svelte index 10c48af..23d672e 100644 --- a/src/routes/admin/zeitraeume/+page.svelte +++ b/src/routes/admin/zeitraeume/+page.svelte @@ -1,175 +1,284 @@ + + try { + const method = bearbeiteId ? 'PATCH' : 'POST'; + const body = bearbeiteId + ? { id: bearbeiteId, bezeichnung: neuerBezeichnung, startDatum: neuerstartDatum, endDatum: neuerendDatum } + : { bezeichnung: neuerBezeichnung, startDatum: neuerstartDatum, endDatum: neuerendDatum }; -
-

Praktikumszeiträume verwalten

+ const res = await fetch('/api/admin/zeitraeume', { + method, + body: JSON.stringify(body), + headers: { 'Content-Type': 'application/json' } + }); - -
- - - - - -
+ await ladeZeitraeume(); + } else { + const err = await res.json(); + fehlermeldung = err.error || 'Fehler beim Speichern'; + } + } catch (err) { + fehlermeldung = err instanceof Error ? err.message : 'Fehler beim Speichern'; + console.error(err); + } + } + + async function loeschen(id: number) { + if (!confirm('Diesen Zeitraum wirklich löschen?')) return; + + try { + const res = await fetch(`/api/admin/zeitraeume?id=${id}`, { method: 'DELETE' }); + + if (!res.ok) { + const err = await res.json(); + fehlermeldung = err.error || 'Fehler beim Löschen'; + return; + } + + await ladeZeitraeume(); + } catch (err) { + fehlermeldung = err instanceof Error ? err.message : 'Fehler beim Löschen'; + console.error(err); + } + } - - {#if fehlermeldung} -

{fehlermeldung}

- {/if} + function resetForm() { + neuerBezeichnung = ''; + neuerstartDatum = ''; + neuerendDatum = ''; + bearbeiteId = null; + } + + onMount(ladeZeitraeume); + - -
-
- -
-
Bezeichnung
-
Startdatum
-
Enddatum
-
Aktionen
-
+ + Praktikumszeiträume verwalten - Admin + - - {#each zeitraeume as d} -
-
{d.bezeichnung}
-
{new Date(d.startDatum).toLocaleDateString('de-DE', { day: '2-digit', month: '2-digit', year: 'numeric' })}
-
{new Date(d.endDatum).toLocaleDateString('de-DE', { day: '2-digit', month: '2-digit', year: 'numeric' })}
-
- - +
+ + +
+ {#if fehlermeldung} +
+
+
+ + + +
+
+

Fehler

+

{fehlermeldung}

- {/each} +
+ {/if} + + +
+

+ {bearbeiteId !== null ? 'Praktikumszeitraum bearbeiten' : 'Neuen Praktikumszeitraum hinzufügen'} +

+ +
+
+ + +
+ +
+ + +
+ +
+ + +
+ +
+ + +
+
-
- -
- -
-
- - \ No newline at end of file + {#if isLoading} +
+
+ Lade Praktikumszeiträume... +
+ {:else if zeitraeume.length === 0} +
+ + + +

Keine Praktikumszeiträume

+

Erstellen Sie Ihren ersten Praktikumszeitraum über das Formular oben.

+
+ {:else} +
+
+

Alle Praktikumszeiträume

+
+ +
+ + + + + + + + + + + {#each zeitraeume as d} + + + + + + + {/each} + +
+ Bezeichnung + + Startdatum + + Enddatum + + Aktionen +
+ {d.bezeichnung} + + {new Date(d.startDatum).toLocaleDateString('de-DE', { + day: '2-digit', + month: '2-digit', + year: 'numeric' + })} + + {new Date(d.endDatum).toLocaleDateString('de-DE', { + day: '2-digit', + month: '2-digit', + year: 'numeric' + })} + + + +
+
+
+ {/if} + +
\ No newline at end of file diff --git a/src/routes/api/admin/zeitraeume/+server.ts b/src/routes/api/admin/zeitraeume/+server.ts index a0560db..145f75c 100644 --- a/src/routes/api/admin/zeitraeume/+server.ts +++ b/src/routes/api/admin/zeitraeume/+server.ts @@ -6,8 +6,9 @@ const prisma = new PrismaClient(); import type { Cookies } from '@sveltejs/kit'; +// Korrigierte Auth-Funktion mit neuem Cookie-Namen function checkAuth(cookies: Cookies) { - return cookies.get('admin_session') === 'true'; + return cookies.get('admin-auth') === 'authenticated'; } function isValidDate(date: string | Date) { @@ -16,73 +17,144 @@ function isValidDate(date: string | Date) { } export const GET: RequestHandler = async ({ cookies }) => { - if (!checkAuth(cookies)) return new Response('Nicht erlaubt', { status: 401 }); - const zeitraeume = await prisma.praktikumszeitraum.findMany(); - return json(zeitraeume); + if (!checkAuth(cookies)) { + return new Response( + JSON.stringify({ error: 'Nicht autorisiert' }), + { + status: 401, + headers: { 'Content-Type': 'application/json' } + } + ); + } + + try { + const zeitraeume = await prisma.praktikumszeitraum.findMany(); + return json(zeitraeume); + } catch (error) { + console.error('Fehler beim Laden der Praktikumszeiträume:', error); + return json({ error: 'Fehler beim Laden der Praktikumszeiträume' }, { status: 500 }); + } }; export const POST: RequestHandler = async ({ cookies, request }) => { - if (!checkAuth(cookies)) return new Response('Nicht erlaubt', { status: 401 }); - const { bezeichnung, startDatum, endDatum } = await request.json(); - if (!isValidDate(startDatum) || !isValidDate(endDatum)) { - return json({ error: 'Ungültige Datum' }, { status: 400 }); + if (!checkAuth(cookies)) { + return json({ error: 'Nicht autorisiert' }, { status: 401 }); } + try { - const created = await prisma.praktikumszeitraum.create({ data: { - bezeichnung, - startDatum: new Date(startDatum), - endDatum: new Date(endDatum) - } }); - return json(created); - } catch (e) { - console.error('Fehler beim Hinzufuegen:', e); - return json({ error: 'Zeitraum existiert bereits' }, { status: 400 }); + const { bezeichnung, startDatum, endDatum } = await request.json(); + + // Validierung + if (!bezeichnung || typeof bezeichnung !== 'string' || bezeichnung.trim().length === 0) { + return json({ error: 'Bezeichnung ist erforderlich' }, { status: 400 }); + } + + if (!isValidDate(startDatum) || !isValidDate(endDatum)) { + return json({ error: 'Ungültiges Datum' }, { status: 400 }); + } + + const created = await prisma.praktikumszeitraum.create({ + data: { + bezeichnung: bezeichnung.trim(), + startDatum: new Date(startDatum), + endDatum: new Date(endDatum) + } + }); + return json(created, { status: 201 }); + } catch (error) { + console.error('Fehler beim Erstellen des Praktikumszeitraums:', error); + return json({ error: 'Fehler beim Erstellen des Praktikumszeitraums' }, { status: 500 }); } }; export const PATCH: RequestHandler = async ({ cookies, request }) => { - if (!checkAuth(cookies)) return new Response('Nicht erlaubt', { status: 401 }); - - const { id, bezeichnung, startDatum, endDatum } = await request.json(); - - if (typeof id !== 'number' || isNaN(id) || !bezeichnung || !isValidDate(startDatum) || !isValidDate(endDatum)) { - return json({ error: 'Ungültige Eingabedaten' }, { status: 400 }); - } - - const existing = await prisma.praktikumszeitraum.findUnique({ where: { id } }); - if (!existing) { - return json({ error: 'Zeitraum nicht gefunden' }, { status: 404 }); - } - - const konflikt = await prisma.praktikumszeitraum.findFirst({ - where: { - bezeichnung, - NOT: { id }, - }, - }); - if (konflikt) { - return json({ error: 'Eine andere Praktikumszeitraum mit diesem Namen existiert bereits' }, { status: 400 }); + if (!checkAuth(cookies)) { + return json({ error: 'Nicht autorisiert' }, { status: 401 }); } try { + const { id, bezeichnung, startDatum, endDatum } = await request.json(); + + // Validierung + if (typeof id !== 'number' || isNaN(id)) { + return json({ error: 'Ungültige ID' }, { status: 400 }); + } + + if (!bezeichnung || typeof bezeichnung !== 'string' || bezeichnung.trim().length === 0) { + return json({ error: 'Bezeichnung ist erforderlich' }, { status: 400 }); + } + + if (!isValidDate(startDatum) || !isValidDate(endDatum)) { + return json({ error: 'Ungültiges Datum' }, { status: 400 }); + } + + // Prüfe ob Praktikumszeitraum existiert + const existing = await prisma.praktikumszeitraum.findUnique({ where: { id } }); + if (!existing) { + return json({ error: 'Praktikumszeitraum nicht gefunden' }, { status: 404 }); + } + + // Prüfe ob neue Bezeichnung bereits bei anderem Zeitraum existiert + const konflikt = await prisma.praktikumszeitraum.findFirst({ + where: { + bezeichnung: bezeichnung.trim(), + NOT: { id }, + }, + }); + + if (konflikt) { + return json({ error: 'Ein anderer Praktikumszeitraum mit dieser Bezeichnung existiert bereits' }, { status: 400 }); + } + const updated = await prisma.praktikumszeitraum.update({ where: { id }, data: { - bezeichnung, + bezeichnung: bezeichnung.trim(), startDatum: new Date(startDatum), endDatum: new Date(endDatum) }, }); + return json(updated); - } catch (e) { - console.error('Fehler beim Update:', e); - return json({ error: 'Update fehlgeschlagen' }, { status: 400 }); + } catch (error) { + console.error('Fehler beim Aktualisieren des Praktikumszeitraums:', error); + return json({ error: 'Fehler beim Aktualisieren des Praktikumszeitraums' }, { status: 500 }); } }; export const DELETE: RequestHandler = async ({ cookies, url }) => { - if (!checkAuth(cookies)) return new Response('Nicht erlaubt', { status: 401 }); + if (!checkAuth(cookies)) { + return json({ error: 'Nicht autorisiert' }, { status: 401 }); + } + const id = Number(url.searchParams.get('id')); - await prisma.praktikumszeitraum.delete({ where: { id } }); - return json({ success: true }); + + if (isNaN(id)) { + return json({ error: 'Ungültige ID' }, { status: 400 }); + } + + try { + // Prüfe ob Praktikumszeitraum existiert + const existing = await prisma.praktikumszeitraum.findUnique({ where: { id } }); + if (!existing) { + return json({ error: 'Praktikumszeitraum nicht gefunden' }, { status: 404 }); + } + + // Hier könntest du prüfen, ob noch Anmeldungen mit diesem Zeitraum verknüpft sind + // const assignedCount = await prisma.anmeldung.count({ + // where: { praktikumszeitraumId: id } + // }); + // + // if (assignedCount > 0) { + // return json({ + // error: 'Praktikumszeitraum kann nicht gelöscht werden. Es sind noch Anmeldungen damit verknüpft.' + // }, { status: 400 }); + // } + + await prisma.praktikumszeitraum.delete({ where: { id } }); + return json({ success: true, message: 'Praktikumszeitraum erfolgreich gelöscht' }); + } catch (error) { + console.error('Fehler beim Löschen des Praktikumszeitraums:', error); + return json({ error: 'Fehler beim Löschen des Praktikumszeitraums' }, { status: 500 }); + } }; \ No newline at end of file