Policies.tsx93 lines · main
1import { useMemo, useState } from 'react'
2import { GenericSkeletonLoader } from 'ui-patterns/ShimmeringLoader'
3
4import { Policies } from '@/components/interfaces/Auth/Policies/Policies'
5import { PoliciesDataProvider } from '@/components/interfaces/Auth/Policies/PoliciesDataContext'
6import { PolicyEditorPanel } from '@/components/interfaces/Auth/Policies/PolicyEditorPanel'
7import type { Policy } from '@/components/interfaces/Auth/Policies/PolicyTableRow/PolicyTableRow.utils'
8import AlertError from '@/components/ui/AlertError'
9import { useDatabasePoliciesQuery } from '@/data/database-policies/database-policies-query'
10import { useTablesQuery } from '@/data/tables/tables-query'
11import { useSelectedProjectQuery } from '@/hooks/misc/useSelectedProject'
12
13export const RealtimePolicies = () => {
14 const { data: project } = useSelectedProjectQuery()
15
16 const [showPolicyEditor, setShowPolicyEditor] = useState(false)
17 const [selectedPolicyToEdit, setSelectedPolicyToEdit] = useState<Policy>()
18
19 const {
20 data: tables,
21 isPending: isLoading,
22 isSuccess,
23 isError,
24 error,
25 } = useTablesQuery({
26 projectRef: project?.ref,
27 connectionString: project?.connectionString,
28 schema: 'realtime',
29 })
30
31 const filteredTables = useMemo(
32 () => (tables ?? []).filter((table) => table.name === 'messages'),
33 [tables]
34 )
35 const visibleTableIds = useMemo(
36 () => new Set(filteredTables.map((table) => table.id)),
37 [filteredTables]
38 )
39 const {
40 data: policies,
41 isPending: isLoadingPolicies,
42 isError: isPoliciesError,
43 error: policiesError,
44 } = useDatabasePoliciesQuery({
45 projectRef: project?.ref,
46 connectionString: project?.connectionString,
47 })
48 // realtime is never in PostgREST's db_schema — skip the config query to avoid a false warning
49 const exposedSchemas = useMemo(() => ['realtime'], [])
50
51 return (
52 <>
53 {isLoading && <GenericSkeletonLoader />}
54
55 {isError && <AlertError error={error} subject="Failed to retrieve tables" />}
56
57 {isSuccess && (
58 <PoliciesDataProvider
59 policies={policies ?? []}
60 isPoliciesLoading={isLoadingPolicies}
61 isPoliciesError={isPoliciesError}
62 policiesError={policiesError ?? undefined}
63 exposedSchemas={exposedSchemas}
64 >
65 <Policies
66 schema="realtime"
67 tables={filteredTables}
68 hasTables
69 isLocked={false}
70 visibleTableIds={visibleTableIds}
71 onSelectCreatePolicy={(_tableName) => {
72 setSelectedPolicyToEdit(undefined)
73 setShowPolicyEditor(true)
74 }}
75 onSelectEditPolicy={(policy) => {
76 setSelectedPolicyToEdit(policy)
77 setShowPolicyEditor(true)
78 }}
79 />
80 </PoliciesDataProvider>
81 )}
82
83 <PolicyEditorPanel
84 visible={showPolicyEditor}
85 searchString="messages"
86 schema="realtime"
87 selectedPolicy={selectedPolicyToEdit}
88 onSelectCancel={() => setShowPolicyEditor(false)}
89 authContext="realtime"
90 />
91 </>
92 )
93}