import { zodResolver } from '@hookform/resolvers/zod'
import { PermissionAction } from '@supabase/shared-types/out/constants'
import { useParams } from 'common'
import { ChevronRight } from 'lucide-react'
import Link from 'next/link'
import { useEffect } from 'react'
import { useForm } from 'react-hook-form'
import { toast } from 'sonner'
import { Button, Card, CardContent, CardFooter, Form, FormControl, FormField, Switch } from 'ui'
import { Admonition } from 'ui-patterns/admonition'
import {
PageSection,
PageSectionContent,
PageSectionMeta,
PageSectionSummary,
PageSectionTitle,
} from 'ui-patterns/PageSection'
import { GenericSkeletonLoader } from 'ui-patterns/ShimmeringLoader'
import * as z from 'zod'
import { TEMPLATES_SCHEMAS } from './AuthTemplatesValidation'
import { slugifyTitle } from './EmailTemplates.utils'
import AlertError from '@/components/ui/AlertError'
import { InlineLink } from '@/components/ui/InlineLink'
import { useAuthConfigQuery } from '@/data/auth/auth-config-query'
import { useAuthConfigUpdateMutation } from '@/data/auth/auth-config-update-mutation'
import { useAsyncCheckPermissions } from '@/hooks/misc/useCheckPermissions'
import { DOCS_URL } from '@/lib/constants'
const notificationEnabledKeys = TEMPLATES_SCHEMAS.filter(
(t) => t.misc?.emailTemplateType === 'security'
).map((template) => {
return `MAILER_NOTIFICATIONS_${template.id?.replace('_NOTIFICATION', '')}_ENABLED`
})
const NotificationsFormSchema = z.object({
...notificationEnabledKeys.reduce(
(acc, key) => {
acc[key] = z.boolean()
return acc
},
{} as Record
),
})
export const EmailTemplates = () => {
const { ref: projectRef } = useParams()
const { can: canUpdateConfig } = useAsyncCheckPermissions(
PermissionAction.UPDATE,
'custom_config_gotrue'
)
const {
data: authConfig,
error: authConfigError,
isPending: isLoading,
isError,
isSuccess,
} = useAuthConfigQuery({ projectRef })
const { mutate: updateAuthConfig, isPending: isUpdatingConfig } = useAuthConfigUpdateMutation({
onError: (error) => {
toast.error(`Failed to update settings: ${error?.message}`)
},
onSuccess: () => {
toast.success('Successfully updated settings')
},
})
const builtInSMTP =
isSuccess &&
authConfig &&
(!authConfig.SMTP_HOST || !authConfig.SMTP_USER || !authConfig.SMTP_PASS)
const defaultValues = notificationEnabledKeys.reduce(
(acc, key) => {
acc[key] = authConfig ? Boolean(authConfig[key as keyof typeof authConfig]) : false
return acc
},
{} as Record
)
const notificationsForm = useForm>({
resolver: zodResolver(NotificationsFormSchema as any),
defaultValues,
})
const onSubmit = (values: any) => {
if (!projectRef) return console.error('Project ref is required')
updateAuthConfig({ projectRef: projectRef, config: { ...values } })
}
useEffect(() => {
if (authConfig) {
notificationsForm.reset(defaultValues)
}
// eslint-disable-next-line react-hooks/exhaustive-deps
}, [authConfig])
return (
<>
{isError && (
)}
{isLoading && (
)}
{isSuccess && (
<>
{builtInSMTP && (
You’re using the built-in email service. This service has rate limits and is not
meant to be used for production apps.{' '}
Learn more
{' '}
}
layout="horizontal"
className="mb-4"
actions={
}
/>
)}
Authentication
{TEMPLATES_SCHEMAS.filter(
(t) => t.misc?.emailTemplateType === 'authentication'
).map((template) => {
const templateSlug = slugifyTitle(template.title)
return (
{template.title}
{template.purpose && (
{template.purpose}
)}
)
})}
Security
>
)}
>
)
}