Show last migration's name instead of timestamp in new home page (#43115)

## Context

In the new project home page, we have a stat for "Last migration" which
we're showing _when_ the last migration was applied. However:
- The timestamp for the migration is derived from the "version" column
of the migration (in the `supabase_migrations` table) which afaik is
derived from the migration's file name
- It'll be alright if the migration was generated via the CLI, but we
can't really enforce the name of the migration file if say they were
generated via AI, so this is technically a point of flakiness
- Reckon that it's more value to show _what_ was the last migration
rather than _when_ so opting to change the value here to show the name
of the last migration instead

### Before
<img width="620" height="311" alt="image"
src="https://github.com/user-attachments/assets/6876acb6-91d2-4ae3-8ce8-98375658c12c"
/>

### After
<img width="582" height="322" alt="image"
src="https://github.com/user-attachments/assets/a40f6635-2068-4edb-a91a-ccf03d8e4d3c"
/>
This commit is contained in:
Joshen Lim
2026-02-25 23:20:23 +08:00
committed by GitHub
parent 26777710d2
commit 9568584fcc
2 changed files with 27 additions and 33 deletions

View File

@@ -1,6 +1,3 @@
import { Search } from 'lucide-react'
import { useState } from 'react'
import { SupportCategories } from '@supabase/shared-types/out/constants'
import { SupportLink } from 'components/interfaces/Support/SupportLink'
import CodeEditor from 'components/ui/CodeEditor/CodeEditor'
@@ -9,6 +6,8 @@ import { DatabaseMigration, useMigrationsQuery } from 'data/database/migrations-
import { useSelectedProjectQuery } from 'hooks/misc/useSelectedProject'
import { DOCS_URL } from 'lib/constants'
import { parseMigrationVersion } from 'lib/migration-utils'
import { Search } from 'lucide-react'
import { useState } from 'react'
import {
Button,
Card,
@@ -24,9 +23,10 @@ import {
TooltipContent,
TooltipTrigger,
} from 'ui'
import { Admonition } from 'ui-patterns'
import { Admonition, TimestampInfo } from 'ui-patterns'
import { Input } from 'ui-patterns/DataInputs/Input'
import { ShimmeringLoader } from 'ui-patterns/ShimmeringLoader'
import { MigrationsEmptyState } from './MigrationsEmptyState'
const Migrations = () => {
@@ -119,9 +119,10 @@ const Migrations = () => {
{migrations.length > 0 ? (
migrations.map((migration) => {
const versionDayjs = parseMigrationVersion(migration.version)
const insertedAt = versionDayjs
const label = versionDayjs
? versionDayjs.format('DD MMM YYYY, HH:mm:ss')
: undefined
: 'Unknown'
const insertedAt = versionDayjs ? versionDayjs.toISOString() : undefined
return (
<TableRow key={migration.version}>
@@ -133,9 +134,19 @@ const Migrations = () => {
>
{migration?.name ?? 'Name not available'}
</TableCell>
<TableCell className={cn(!insertedAt && 'text-foreground-lighter')}>
<TableCell>
<Tooltip>
<TooltipTrigger>{insertedAt ?? 'Unknown'}</TooltipTrigger>
<TooltipTrigger>
{!!insertedAt ? (
<TimestampInfo
className="text-sm"
label={label}
utcTimestamp={insertedAt}
/>
) : (
<p className="text-foreground-lighter">Unknown</p>
)}
</TooltipTrigger>
{!insertedAt && (
<TooltipContent side="right" className="w-64 text-center">
This migration was not generated via the{' '}

View File

@@ -5,13 +5,13 @@ import { useBackupsQuery } from 'data/database/backups-query'
import { DatabaseMigration, useMigrationsQuery } from 'data/database/migrations-query'
import dayjs from 'dayjs'
import { useSelectedProjectQuery } from 'hooks/misc/useSelectedProject'
import { parseMigrationVersion } from 'lib/migration-utils'
import { Archive, Database, GitBranch } from 'lucide-react'
import { useMemo } from 'react'
import { cn, Skeleton } from 'ui'
import { TimestampInfo } from 'ui-patterns'
import { ServiceStatus } from './ServiceStatus'
import { EMPTY_ARR } from '@/lib/void'
export const ActivityStats = () => {
const { ref } = useParams()
@@ -37,14 +37,16 @@ export const ActivityStats = () => {
)[0]
}, [branchesData])
const { data: migrationsData, isPending: isLoadingMigrations } = useMigrationsQuery({
const { data: migrationsData = EMPTY_ARR, isPending: isLoadingMigrations } = useMigrationsQuery({
projectRef: project?.ref,
connectionString: project?.connectionString,
})
const latestMigration = useMemo<DatabaseMigration | undefined>(
() => (migrationsData ?? [])[0],
() => migrationsData[0],
[migrationsData]
)
const migrationLabelText =
migrationsData.length === 0 ? 'No migrations' : latestMigration?.name ?? 'Unknown'
const { data: backupsData, isPending: isLoadingBackups } = useBackupsQuery({
projectRef: project?.ref,
@@ -57,21 +59,6 @@ export const ActivityStats = () => {
.sort((a, b) => new Date(b.inserted_at).valueOf() - new Date(a.inserted_at).valueOf())[0]
}, [backupsData])
const [versionLabel, versionTimestamp] = useMemo(() => {
const version = latestMigration?.version
const versionDayjs = parseMigrationVersion(version)
if (versionDayjs) {
return [versionDayjs.fromNow(), versionDayjs.toISOString()]
}
return [undefined, undefined]
}, [latestMigration])
const hasValidVersion = versionLabel && versionTimestamp
const versionLabelText = migrationsData && migrationsData.length > 0 ? 'Unknown' : 'No migrations'
return (
<div className="@container">
<div className="grid grid-cols-1 @md:grid-cols-2 gap-2 @md:gap-6 flex-wrap">
@@ -88,14 +75,10 @@ export const ActivityStats = () => {
value={
isLoadingMigrations ? (
<Skeleton className="h-6 w-24" />
) : hasValidVersion ? (
<TimestampInfo
className="text-base"
label={versionLabel}
utcTimestamp={versionTimestamp}
/>
) : (
<p className="text-foreground-lighter">{versionLabelText}</p>
<p className={!!latestMigration ? 'text-foreground' : 'text-foreground-lighter'}>
{migrationLabelText}
</p>
)
}
/>