mirror of
https://github.com/supabase/supabase.git
synced 2026-10-15 14:19:11 +03:00
update styling
This commit is contained in:
1 parent
a25a761863
commit
12b4e6fa8f
4 files changed
+135
-111
No files matched your search
@@ -5,17 +5,7 @@ import {
|
||||
type EdgeFunctionBodyData,
|
||||
} from 'data/edge-functions/edge-function-body-query'
|
||||
import type { EdgeFunctionsData } from 'data/edge-functions/edge-functions-query'
|
||||
import {
|
||||
Card,
|
||||
CardContent,
|
||||
CardHeader,
|
||||
CardTitle,
|
||||
cn,
|
||||
Skeleton,
|
||||
Tabs_Shadcn_,
|
||||
TabsList_Shadcn_,
|
||||
TabsTrigger_Shadcn_,
|
||||
} from 'ui'
|
||||
import { Card, CardContent, CardHeader, CardTitle, cn, Skeleton } from 'ui'
|
||||
import { Code, Wind } from 'lucide-react'
|
||||
import Link from 'next/link'
|
||||
import { useEffect, useMemo, useState } from 'react'
|
||||
@@ -96,41 +86,56 @@ const FunctionDiff = ({
|
||||
|
||||
return (
|
||||
<Card>
|
||||
<CardHeader className="space-y-0">
|
||||
<CardHeader className="space-y-0 px-4">
|
||||
{/* Function title */}
|
||||
<Link
|
||||
href={`/project/${currentBranchRef}/functions/${functionSlug}`}
|
||||
className="text-sm text-foreground-light flex items-center gap-2"
|
||||
>
|
||||
<Code strokeWidth={1.5} size={16} className="text-foreground-light" />
|
||||
{functionSlug}
|
||||
</Link>
|
||||
|
||||
{/* File tabs */}
|
||||
{diffFileKeys.length > 1 && (
|
||||
<Tabs_Shadcn_
|
||||
value={activeFileKey ?? diffFileKeys[0]}
|
||||
onValueChange={(v: string) => setActiveFileKey(v)}
|
||||
<CardTitle>
|
||||
<Link
|
||||
href={`/project/${currentBranchRef}/functions/${functionSlug}`}
|
||||
className="flex items-center gap-2"
|
||||
>
|
||||
<TabsList_Shadcn_ className="gap-4 overflow-x-auto border-b-0 -mx-6 -mb-4 mt-1 px-6">
|
||||
{diffFileKeys.map((key) => (
|
||||
<TabsTrigger_Shadcn_ key={key} value={key}>
|
||||
{key}
|
||||
</TabsTrigger_Shadcn_>
|
||||
))}
|
||||
</TabsList_Shadcn_>
|
||||
</Tabs_Shadcn_>
|
||||
)}
|
||||
<Code strokeWidth={1.5} size={16} className="text-foreground-light" />
|
||||
{functionSlug}
|
||||
</Link>
|
||||
</CardTitle>
|
||||
|
||||
{/* File list sidebar will be shown instead of top tabs */}
|
||||
</CardHeader>
|
||||
<CardContent className="p-0 h-96">
|
||||
<DiffEditor
|
||||
theme="supabase"
|
||||
language={language}
|
||||
height="100%"
|
||||
original={mainFile?.content || ''}
|
||||
modified={currentFile?.content || ''}
|
||||
options={defaultOptions}
|
||||
/>
|
||||
<div className="flex h-full min-h-0">
|
||||
{/* Sidebar file list */}
|
||||
<div className="w-48 border-r bg-surface-200 flex flex-col overflow-y-auto">
|
||||
<ul className="divide-y divide-border">
|
||||
{diffFileKeys.map((key) => (
|
||||
<li key={key} className="flex">
|
||||
<button
|
||||
type="button"
|
||||
onClick={() => setActiveFileKey(key)}
|
||||
className={cn(
|
||||
'flex-1 text-left text-xs px-4 py-2 flex items-center gap-2',
|
||||
activeFileKey === key
|
||||
? 'bg-surface-300 text-foreground'
|
||||
: 'text-foreground-light hover:bg-surface-300'
|
||||
)}
|
||||
>
|
||||
{key}
|
||||
</button>
|
||||
</li>
|
||||
))}
|
||||
</ul>
|
||||
</div>
|
||||
|
||||
{/* Diff viewer */}
|
||||
<div className="flex-1 min-h-0">
|
||||
<DiffEditor
|
||||
theme="supabase"
|
||||
language={language}
|
||||
height="100%"
|
||||
original={mainFile?.content || ''}
|
||||
modified={currentFile?.content || ''}
|
||||
options={defaultOptions}
|
||||
/>
|
||||
</div>
|
||||
</div>
|
||||
</CardContent>
|
||||
</Card>
|
||||
)
|
||||
|
||||
@@ -15,8 +15,8 @@ import {
|
||||
import { ScaffoldDescription, ScaffoldTitle } from '../Scaffold'
|
||||
|
||||
interface PageHeaderProps {
|
||||
title?: string
|
||||
subtitle?: string
|
||||
title?: string | ReactNode
|
||||
subtitle?: string | ReactNode
|
||||
icon?: ReactNode
|
||||
breadcrumbs?: Array<{
|
||||
label?: string
|
||||
|
||||
@@ -14,6 +14,7 @@ export interface NavigationItem {
|
||||
icon?: ReactNode
|
||||
onClick?: () => void
|
||||
badge?: string
|
||||
active?: boolean
|
||||
}
|
||||
|
||||
interface PageLayoutProps {
|
||||
@@ -102,38 +103,42 @@ export const PageLayout = ({
|
||||
{/* Navigation section */}
|
||||
{navigationItems.length > 0 && (
|
||||
<NavMenu className={cn(isCompact ? 'mt-2' : 'mt-4', size === 'full' && 'border-none')}>
|
||||
{navigationItems.map((item) => (
|
||||
<NavMenuItem key={item.label} active={router.asPath.split('?')[0] === item.href}>
|
||||
{item.href ? (
|
||||
<Link
|
||||
href={
|
||||
item.href.includes('[ref]') && !!ref
|
||||
? item.href.replace('[ref]', ref)
|
||||
: item.href
|
||||
}
|
||||
className={cn(
|
||||
'inline-flex items-center gap-2',
|
||||
router.asPath === item.href && 'text-foreground'
|
||||
)}
|
||||
onClick={item.onClick}
|
||||
>
|
||||
{item.icon && <span>{item.icon}</span>}
|
||||
{item.label}
|
||||
{item.badge && <Badge variant="default">{item.badge}</Badge>}
|
||||
</Link>
|
||||
) : (
|
||||
<Button
|
||||
type="link"
|
||||
onClick={item.onClick}
|
||||
className={cn(router.pathname === item.href && 'text-foreground font-medium')}
|
||||
>
|
||||
{item.icon && <span className="mr-2">{item.icon}</span>}
|
||||
{item.label}
|
||||
{item.badge && <Badge variant="default">{item.badge}</Badge>}
|
||||
</Button>
|
||||
)}
|
||||
</NavMenuItem>
|
||||
))}
|
||||
{navigationItems.map((item) => {
|
||||
const isActive =
|
||||
item.active !== undefined ? item.active : router.asPath.split('?')[0] === item.href
|
||||
return (
|
||||
<NavMenuItem key={item.label} active={isActive}>
|
||||
{item.href ? (
|
||||
<Link
|
||||
href={
|
||||
item.href.includes('[ref]') && !!ref
|
||||
? item.href.replace('[ref]', ref)
|
||||
: item.href
|
||||
}
|
||||
className={cn(
|
||||
'inline-flex items-center gap-2',
|
||||
isActive && 'text-foreground'
|
||||
)}
|
||||
onClick={item.onClick}
|
||||
>
|
||||
{item.icon && <span>{item.icon}</span>}
|
||||
{item.label}
|
||||
{item.badge && <Badge variant="default">{item.badge}</Badge>}
|
||||
</Link>
|
||||
) : (
|
||||
<Button
|
||||
type="link"
|
||||
onClick={item.onClick}
|
||||
className={cn(isActive && 'text-foreground font-medium')}
|
||||
>
|
||||
{item.icon && <span className="mr-2">{item.icon}</span>}
|
||||
{item.label}
|
||||
{item.badge && <Badge variant="default">{item.badge}</Badge>}
|
||||
</Button>
|
||||
)}
|
||||
</NavMenuItem>
|
||||
)
|
||||
})}
|
||||
</NavMenu>
|
||||
)}
|
||||
</ScaffoldContainer>
|
||||
|
||||
@@ -16,12 +16,6 @@ import { useEdgeFunctionsQuery } from 'data/edge-functions/edge-functions-query'
|
||||
import DatabaseDiffPanel from 'components/interfaces/BranchManagement/DatabaseDiffPanel'
|
||||
import EdgeFunctionsDiffPanel from 'components/interfaces/BranchManagement/EdgeFunctionsDiffPanel'
|
||||
import { Badge, Button } from 'ui'
|
||||
import {
|
||||
Tabs_Shadcn_ as Tabs,
|
||||
TabsContent_Shadcn_ as TabsContent,
|
||||
TabsList_Shadcn_ as TabsList,
|
||||
TabsTrigger_Shadcn_ as TabsTrigger,
|
||||
} from 'ui'
|
||||
import { toast } from 'sonner'
|
||||
import type { NextPageWithLayout } from 'types'
|
||||
import { ScaffoldContainer } from 'components/layouts/Scaffold'
|
||||
@@ -211,6 +205,32 @@ const MergePage: NextPageWithLayout = () => {
|
||||
[diffContent, currentBranchFunctions, mainBranchFunctions]
|
||||
)
|
||||
|
||||
// Determine current active tab via query param (defaults to 'database')
|
||||
const currentTab = (router.query.tab as string) || 'database'
|
||||
|
||||
// Navigation items for PageLayout - updates the `tab` query param
|
||||
const navigationItems = useMemo(() => {
|
||||
const buildHref = (tab: string) => {
|
||||
const query: Record<string, string> = { tab }
|
||||
if (workflowRunId) query.workflow_run_id = workflowRunId
|
||||
const qs = new URLSearchParams(query).toString()
|
||||
return `/project/[ref]/merge?${qs}`
|
||||
}
|
||||
|
||||
return [
|
||||
{
|
||||
label: 'Database',
|
||||
href: buildHref('database'),
|
||||
active: currentTab === 'database',
|
||||
},
|
||||
{
|
||||
label: 'Edge Functions',
|
||||
href: buildHref('edge-functions'),
|
||||
active: currentTab === 'edge-functions',
|
||||
},
|
||||
]
|
||||
}, [workflowRunId, currentTab])
|
||||
|
||||
if (!isBranch || !currentBranch) {
|
||||
return (
|
||||
<PageLayout title="Merge Request">
|
||||
@@ -283,8 +303,10 @@ const MergePage: NextPageWithLayout = () => {
|
||||
subtitle={pageSubtitle()}
|
||||
breadcrumbs={breadcrumbs}
|
||||
primaryActions={primaryActions}
|
||||
size="full"
|
||||
navigationItems={navigationItems}
|
||||
>
|
||||
<ScaffoldContainer className="pt-6 pb-12">
|
||||
<ScaffoldContainer size="full" className="pt-6 pb-12">
|
||||
{/* Merge workflow logs */}
|
||||
<WorkflowLogsCard
|
||||
attemptedMerge={attemptedMerge}
|
||||
@@ -295,34 +317,26 @@ const MergePage: NextPageWithLayout = () => {
|
||||
mainBranchRef={mainBranch?.project_ref}
|
||||
/>
|
||||
|
||||
<Tabs defaultValue="database" className="w-full">
|
||||
<TabsList className="gap-4 mb-8">
|
||||
<TabsTrigger value="database">Database</TabsTrigger>
|
||||
<TabsTrigger value="edge-functions">Edge Functions</TabsTrigger>
|
||||
</TabsList>
|
||||
|
||||
<TabsContent value="database">
|
||||
<DatabaseDiffPanel
|
||||
diffContent={diffContent}
|
||||
isLoading={isDiffLoading}
|
||||
error={diffError}
|
||||
showRefreshButton={!isPolling}
|
||||
onRefresh={() => refetchDiff()}
|
||||
currentBranchRef={ref}
|
||||
/>
|
||||
</TabsContent>
|
||||
|
||||
<TabsContent value="edge-functions">
|
||||
<EdgeFunctionsDiffPanel
|
||||
currentBranchFunctions={currentBranchFunctions}
|
||||
mainBranchFunctions={mainBranchFunctions}
|
||||
isCurrentFunctionsLoading={isCurrentFunctionsLoading}
|
||||
isMainFunctionsLoading={isMainFunctionsLoading}
|
||||
currentBranchRef={ref}
|
||||
mainBranchRef={parentProjectRef}
|
||||
/>
|
||||
</TabsContent>
|
||||
</Tabs>
|
||||
{/* Content based on selected tab */}
|
||||
{currentTab === 'database' ? (
|
||||
<DatabaseDiffPanel
|
||||
diffContent={diffContent}
|
||||
isLoading={isDiffLoading}
|
||||
error={diffError}
|
||||
showRefreshButton={!isPolling}
|
||||
onRefresh={() => refetchDiff()}
|
||||
currentBranchRef={ref}
|
||||
/>
|
||||
) : (
|
||||
<EdgeFunctionsDiffPanel
|
||||
currentBranchFunctions={currentBranchFunctions}
|
||||
mainBranchFunctions={mainBranchFunctions}
|
||||
isCurrentFunctionsLoading={isCurrentFunctionsLoading}
|
||||
isMainFunctionsLoading={isMainFunctionsLoading}
|
||||
currentBranchRef={ref}
|
||||
mainBranchRef={parentProjectRef}
|
||||
/>
|
||||
)}
|
||||
</ScaffoldContainer>
|
||||
</PageLayout>
|
||||
)
|
||||
|
||||
Reference in new issue
Block a user