| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190 |
- "use client";
- import React from "react";
- import { Loader2 } from "lucide-react";
- import { normalizeBranchIdDraft } from "@/components/admin/users/usersUi";
- import { CREATE_ROLE_OPTIONS } from "@/components/admin/users/create-user/createUserUtils";
- import { Button } from "@/components/ui/button";
- import { Input } from "@/components/ui/input";
- import { Label } from "@/components/ui/label";
- import { Alert, AlertTitle, AlertDescription } from "@/components/ui/alert";
- import { DialogFooter } from "@/components/ui/dialog";
- import {
- DropdownMenu,
- DropdownMenuContent,
- DropdownMenuLabel,
- DropdownMenuRadioGroup,
- DropdownMenuRadioItem,
- DropdownMenuSeparator,
- DropdownMenuTrigger,
- } from "@/components/ui/dropdown-menu";
- function RoleSelect({ value, onChange, disabled }) {
- const label =
- CREATE_ROLE_OPTIONS.find((x) => x.value === value)?.label || "Rolle wählen";
- return (
- <div className="grid gap-2">
- <Label>Rolle</Label>
- <DropdownMenu>
- <DropdownMenuTrigger asChild>
- <Button type="button" variant="outline" disabled={disabled}>
- {label}
- </Button>
- </DropdownMenuTrigger>
- <DropdownMenuContent align="start" className="min-w-56">
- <DropdownMenuLabel>Rolle auswählen</DropdownMenuLabel>
- <DropdownMenuSeparator />
- <DropdownMenuRadioGroup value={value} onValueChange={onChange}>
- {CREATE_ROLE_OPTIONS.map((opt) => (
- <DropdownMenuRadioItem key={opt.value} value={opt.value}>
- {opt.label}
- </DropdownMenuRadioItem>
- ))}
- </DropdownMenuRadioGroup>
- </DropdownMenuContent>
- </DropdownMenu>
- </div>
- );
- }
- export default function CreateUserForm({
- form,
- setPatch,
- error,
- policyLines,
- disabled,
- isSubmitting,
- onCancel,
- onSubmit,
- }) {
- const role = String(form?.role || "branch");
- return (
- <form onSubmit={onSubmit} className="space-y-4">
- {error ? (
- <Alert variant="destructive">
- <AlertTitle>{error.title}</AlertTitle>
- {error.description ? (
- <AlertDescription>{error.description}</AlertDescription>
- ) : null}
- {Array.isArray(error.hints) && error.hints.length > 0 ? (
- <AlertDescription>
- <ul className="mt-2 list-disc pl-5">
- {error.hints.map((line) => (
- <li key={line}>{line}</li>
- ))}
- </ul>
- </AlertDescription>
- ) : null}
- </Alert>
- ) : null}
- <div className="grid gap-3 md:grid-cols-2">
- <div className="grid gap-2">
- <Label htmlFor="cu-username">Benutzername</Label>
- <Input
- id="cu-username"
- value={form?.username ?? ""}
- onChange={(e) => setPatch({ username: e.target.value })}
- disabled={disabled}
- autoCapitalize="none"
- autoCorrect="off"
- spellCheck={false}
- placeholder="z. B. branchuser"
- />
- </div>
- <div className="grid gap-2">
- <Label htmlFor="cu-email">E-Mail</Label>
- <Input
- id="cu-email"
- value={form?.email ?? ""}
- onChange={(e) => setPatch({ email: e.target.value })}
- disabled={disabled}
- placeholder="name@firma.de"
- />
- </div>
- </div>
- <div className="grid gap-3 md:grid-cols-2">
- <RoleSelect
- value={role}
- onChange={(v) => setPatch({ role: v })}
- disabled={disabled}
- />
- {role === "branch" ? (
- <div className="grid gap-2">
- <Label htmlFor="cu-branch">Niederlassung</Label>
- <Input
- id="cu-branch"
- value={form?.branchId ?? ""}
- onChange={(e) => setPatch({ branchId: e.target.value })}
- disabled={disabled}
- placeholder="z. B. NL01"
- />
- </div>
- ) : (
- <div className="grid gap-2">
- <Label>Niederlassung</Label>
- <Input value="—" disabled />
- </div>
- )}
- </div>
- {/* Keep branchId normalized as user types (optional UX polish) */}
- {role === "branch" ? (
- <div className="text-xs text-muted-foreground">
- Aktuell: {normalizeBranchIdDraft(form?.branchId || "") || "—"}
- </div>
- ) : null}
- <div className="grid gap-2">
- <Label htmlFor="cu-password">Initiales Passwort</Label>
- <Input
- id="cu-password"
- type="password"
- value={form?.initialPassword ?? ""}
- onChange={(e) => setPatch({ initialPassword: e.target.value })}
- disabled={disabled}
- placeholder="••••••••"
- />
- <ul className="mt-1 list-disc pl-5 text-xs text-muted-foreground">
- {(Array.isArray(policyLines) ? policyLines : []).map((line) => (
- <li key={line}>{line}</li>
- ))}
- </ul>
- </div>
- <DialogFooter>
- <Button
- type="button"
- variant="outline"
- disabled={disabled}
- onClick={onCancel}
- >
- Abbrechen
- </Button>
- <Button type="submit" disabled={disabled}>
- {isSubmitting ? (
- <>
- <Loader2 className="h-4 w-4 animate-spin" />
- Speichern…
- </>
- ) : (
- "Anlegen"
- )}
- </Button>
- </DialogFooter>
- </form>
- );
- }
|