import { zodResolver } from "@hookform/resolvers/zod"; import { GlobeIcon } from "lucide-react"; import { useTranslation } from "next-i18next"; import { useEffect } from "react"; import { useForm } from "react-hook-form"; import { toast } from "sonner"; import { z } from "zod"; import { AlertBlock } from "@/components/shared/alert-block"; import { Button } from "@/components/ui/button"; import { Card, CardContent, CardDescription, CardHeader, CardTitle, } from "@/components/ui/card"; import { Form, FormControl, FormDescription, FormField, FormItem, FormLabel, FormMessage, } from "@/components/ui/form"; import { Input } from "@/components/ui/input"; import { Select, SelectContent, SelectItem, SelectTrigger, SelectValue, } from "@/components/ui/select"; import { Switch } from "@/components/ui/switch"; import { api } from "@/utils/api"; const addServerDomain = z .object({ domain: z.string(), letsEncryptEmail: z.string(), https: z.boolean().optional(), certificateType: z.enum(["letsencrypt", "none", "custom"]), }) .superRefine((data, ctx) => { if (data.https && !data.certificateType) { ctx.addIssue({ code: z.ZodIssueCode.custom, path: ["certificateType"], message: "Required", }); } if (data.certificateType === "letsencrypt" && !data.letsEncryptEmail) { ctx.addIssue({ code: z.ZodIssueCode.custom, message: "LetsEncrypt email is required when certificate type is letsencrypt", path: ["letsEncryptEmail"], }); } }); type AddServerDomain = z.infer; export const WebDomain = () => { const { t } = useTranslation("settings"); const { data, refetch } = api.user.get.useQuery(); const { mutateAsync, isLoading } = api.settings.assignDomainServer.useMutation(); const form = useForm({ defaultValues: { domain: "", certificateType: "none", letsEncryptEmail: "", https: false, }, resolver: zodResolver(addServerDomain), }); const https = form.watch("https"); const domain = form.watch("domain") || ""; const host = data?.user?.host || ""; const hasChanged = domain !== host; useEffect(() => { if (data) { form.reset({ domain: data?.user?.host || "", certificateType: data?.user?.certificateType, letsEncryptEmail: data?.user?.letsEncryptEmail || "", https: data?.user?.https || false, }); } }, [form, form.reset, data]); const onSubmit = async (data: AddServerDomain) => { await mutateAsync({ host: data.domain, letsEncryptEmail: data.letsEncryptEmail, certificateType: data.certificateType, https: data.https, }) .then(async () => { await refetch(); toast.success("Domain Assigned"); }) .catch(() => { toast.error("Error assigning the domain"); }); }; return (
{t("settings.server.domain.title")} {t("settings.server.domain.description")}
{/* Warning for GitHub webhook URL changes */} {hasChanged && (

⚠️ Important: URL Change Impact

If you change the Dokploy Server URL make sure to update your Github Apps to keep the auto-deploy working and preview deployments working.

)}
{ return ( {t("settings.server.domain.form.domain")} ); }} /> { return ( {t("settings.server.domain.form.letsEncryptEmail")} ); }} /> (
HTTPS Automatically provision SSL Certificate.
)} /> {https && ( { return ( {t("settings.server.domain.form.certificate.label")} ); }} /> )}
); };