chore: Use @supabase/config for the code configuration page (#50398)

How to test:
1. Connect a project to GH repo
2. Deploy the `config.toml` once
3. Change some setting in Auth
4. You should see a change in
`/dashboard/project/_/settings/code-configuration`

<img width="1271" height="1186" alt="Screenshot 2026-09-16 at 16 26 39"
src="https://github.com/user-attachments/assets/dfc135a4-e495-489e-88fd-b760383793b4"
/>

<!-- This is an auto-generated comment: release notes by coderabbit.ai
-->
## Summary by CodeRabbit

- **New Features**
- Configuration drift comparisons now use a consistent project
configuration schema.
- Drift details display complete current-environment and `config.toml`
values, grouped by section.
- Matching and unmanaged settings are organized into dedicated sections.
  - Configuration fields link directly to relevant Studio settings.
  - Added a warning that GitHub deployments overwrite local changes.

- **Bug Fixes**
- Configuration updates now refresh project configuration data
automatically.
  - Improved labels and formatting for boolean and redirect URL values.
- Drift errors identify invalid configuration paths and provide
corrective guidance.
<!-- end of auto-generated comment: release notes by coderabbit.ai -->
This commit is contained in:
Ivan Vasilov authored and GitHub committed 2026-09-21 16:38:37 +02:00
1 parent be9c67a761
commit 8422045b86
30 files changed
+1873 -1899

No files matched your search

+52 -9
View File
@@ -2,8 +2,12 @@ import { useQuery } from '@tanstack/react-query'
import { useParams } from 'common'
import { useCallback, useMemo } from 'react'
import { convertProjectConfigToGitHubConfig } from '@/components/interfaces/ConfigDrift/github-config-convert'
import { getConfigDriftSummary } from '@/components/interfaces/ConfigDrift/github-config-drift'
import {
formatGitHubConfigDecodeMessage,
fromDashboardProjectConfig,
getConfigDriftSummary,
type GitHubConfigDriftSummary,
} from '@/components/interfaces/ConfigDrift/github-config-drift'
import type { Branch } from '@/data/branches/branches-query'
import { useBranchesQuery } from '@/data/branches/branches-query'
import { useGitHubConfigQuery } from '@/data/config/github-config-query'
@@ -12,6 +16,16 @@ import { useProjectGitHubConnectionQuery } from '@/data/integrations/github-conn
import { useSelectedProjectQuery } from '@/hooks/misc/useSelectedProject'
import { IS_PLATFORM } from '@/lib/constants'
const EMPTY_SUMMARY: GitHubConfigDriftSummary = {
driftedFields: [],
matchedFields: [],
unmanagedFields: [],
}
type ConfigDriftMemoResult =
| { status: 'success'; summary: GitHubConfigDriftSummary }
| { status: 'error'; source: 'project-config' | 'config-toml'; error: Error }
export function getGitBranchName(branch?: Branch): string | undefined {
return branch?.git_branch?.trim() || (branch?.is_default ? undefined : branch?.name?.trim())
}
@@ -59,15 +73,37 @@ export function useSelectedGitHubConfigDrift() {
[branchesRefetch, connectionRefetch, projectConfigRefetch, githubConfigRefetch]
)
const summary = useMemo(() => {
const dashboardConfig = convertProjectConfigToGitHubConfig(projectConfigQuery.data?.attributes)
const driftResult = useMemo((): ConfigDriftMemoResult => {
let dashboardConfig
try {
dashboardConfig = fromDashboardProjectConfig(projectConfigQuery.data?.attributes)
} catch (error) {
console.error('Failed to read project configuration:', error)
return {
status: 'error',
source: 'project-config',
error: new Error('Could not read the project configuration returned by the API.'),
}
}
return getConfigDriftSummary({
dashboardConfig: dashboardConfig,
const result = getConfigDriftSummary({
dashboardConfig,
githubConfig: githubConfigQuery.data?.config,
})
if (result.status === 'invalid-config') {
return {
status: 'error',
source: 'config-toml',
error: new Error(formatGitHubConfigDecodeMessage(result.issues)),
}
}
return { status: 'success', summary: result.summary }
}, [projectConfigQuery.data?.attributes, githubConfigQuery.data?.config])
const summary = driftResult.status === 'success' ? driftResult.summary : EMPTY_SUMMARY
const conversionError = driftResult.status === 'error' ? driftResult.error : undefined
const activeQueries = [
projectQuery,
...(shouldLoad ? [branchesQuery, connectionQuery] : []),
@@ -77,16 +113,23 @@ export function useSelectedGitHubConfigDrift() {
const isReady =
shouldLoad && hasConnection && projectConfigQuery.isSuccess && githubConfigQuery.isSuccess
const issueCount = summary.driftedFields.length
const queryError = activeQueries.find((query) => query.error)?.error
let errorSource: 'query' | 'project-config' | 'config-toml' | undefined = undefined
if (queryError) {
errorSource = 'query'
} else if (driftResult.status === 'error') {
errorSource = driftResult.source
}
return {
requestedGitBranch: gitBranch,
isReady,
isPending: activeQueries.some((query) => query.isPending),
isFetching: activeQueries.some((query) => query.isFetching),
isError: activeQueries.some((query) => query.isError),
error: activeQueries.find((query) => query.error)?.error,
isError: activeQueries.some((query) => query.isError) || conversionError !== undefined,
error: queryError ?? conversionError,
errorSource,
hasConfigurationIssues: isReady && issueCount > 0,
unmanagedFields: summary.unmanagedFields,
summary,
refetch,
}