SecurityOptions.tsx157 lines · main
1import { UseFormReturn } from 'react-hook-form'
2import {
3 Checkbox,
4 cn,
5 FormControl,
6 FormDescription,
7 FormField,
8 FormItem,
9 FormLabel,
10 Tooltip,
11 TooltipContent,
12 TooltipTrigger,
13 useWatch,
14} from 'ui'
15import { Admonition } from 'ui-patterns'
16import { FormItemLayout } from 'ui-patterns/form/FormItemLayout/FormItemLayout'
17
18import { CreateProjectForm } from './ProjectCreation.schema'
19import { InlineLink } from '@/components/ui/InlineLink'
20import Panel from '@/components/ui/Panel'
21import { useTrackDefaultPrivilegesExposure } from '@/hooks/misc/useDataApiRevokeOnCreateDefault'
22import { DOCS_URL } from '@/lib/constants'
23
24interface SecurityOptionsProps {
25 form: UseFormReturn<CreateProjectForm>
26 layout?: 'vertical' | 'horizontal'
27}
28
29export const SecurityOptions = ({ form, layout = 'horizontal' }: SecurityOptionsProps) => {
30 const dataApi = useWatch({ control: form.control, name: 'dataApi' })
31 const dataApiDefaultPrivileges = useWatch({
32 control: form.control,
33 name: 'dataApiDefaultPrivileges',
34 })
35 const hasUserModified = form.getFieldState('dataApiDefaultPrivileges', form.formState).isDirty
36
37 useTrackDefaultPrivilegesExposure({
38 surface: 'main',
39 dataApiDefaultPrivileges: dataApiDefaultPrivileges ?? true,
40 hasUserModified,
41 })
42
43 return (
44 <Panel.Content className="pb-8">
45 <FormItemLayout layout={layout} label="Security" isReactForm={false}>
46 <div className="flex flex-col gap-4">
47 <FormField
48 name="dataApi"
49 control={form.control}
50 render={({ field }) => (
51 <FormItem className="flex items-start gap-3">
52 <FormControl>
53 <Checkbox
54 checked={field.value}
55 disabled={field.disabled}
56 onCheckedChange={(value) => field.onChange(value === true)}
57 />
58 </FormControl>
59 <div className="space-y-1">
60 <FormLabel className="text-sm text-foreground">Enable Data API</FormLabel>
61 <FormDescription className="text-foreground-lighter">
62 Autogenerate a RESTful API for your public schema. Recommended if using a client
63 library like{' '}
64 <InlineLink href={`${DOCS_URL}/reference/javascript/introduction`}>
65 briven-js
66 </InlineLink>
67 .
68 </FormDescription>
69 </div>
70 </FormItem>
71 )}
72 />
73
74 <FormField
75 name="dataApiDefaultPrivileges"
76 control={form.control}
77 render={({ field }) => (
78 <FormItem
79 className={cn(
80 'flex items-start gap-3',
81 !dataApi && 'opacity-50 cursor-not-allowed'
82 )}
83 >
84 <FormControl>
85 {dataApi ? (
86 <Checkbox
87 checked={field.value}
88 disabled={field.disabled}
89 onCheckedChange={(value) => field.onChange(value === true)}
90 />
91 ) : (
92 <Tooltip>
93 <TooltipTrigger asChild>
94 <span className="cursor-not-allowed">
95 <Checkbox checked={field.value} disabled />
96 </span>
97 </TooltipTrigger>
98 <TooltipContent side="top">
99 Enable the Data API to configure default privileges.
100 </TooltipContent>
101 </Tooltip>
102 )}
103 </FormControl>
104 <div className="space-y-1">
105 <FormLabel
106 className={cn('text-sm text-foreground', !dataApi && 'text-foreground-muted')}
107 >
108 Automatically expose new tables
109 </FormLabel>
110 <FormDescription className="text-foreground-lighter">
111 Grants privileges to Data API roles by default, exposing new tables.
112 <br />
113 <strong className="font-medium text-foreground-light">
114 We recommend disabling this to control access manually.
115 </strong>
116 </FormDescription>
117 </div>
118 </FormItem>
119 )}
120 />
121
122 <FormField
123 name="enableRlsEventTrigger"
124 control={form.control}
125 render={({ field }) => (
126 <FormItem className="flex items-start gap-3">
127 <FormControl>
128 <Checkbox
129 checked={field.value}
130 disabled={field.disabled}
131 onCheckedChange={(value) => field.onChange(value === true)}
132 />
133 </FormControl>
134 <div className="space-y-1">
135 <FormLabel className="text-sm text-foreground">Enable automatic RLS</FormLabel>
136 <FormDescription className="text-foreground-lighter">
137 Create an event trigger that automatically enables Row Level Security on all new
138 tables in the public schema.
139 </FormDescription>
140 </div>
141 </FormItem>
142 )}
143 />
144
145 {!dataApi && (
146 <Admonition
147 type="warning"
148 title="Client libraries need Data API to query your database"
149 >
150 Disabling it means briven-js and similar libraries can't query or mutate data.
151 </Admonition>
152 )}
153 </div>
154 </FormItemLayout>
155 </Panel.Content>
156 )
157}