Skip to content

Commit

Permalink
chore: merge upstream updates
Browse files Browse the repository at this point in the history
  • Loading branch information
jingsam committed Sep 11, 2024
2 parents f2f5cbe + 9e1d6f9 commit c1b2b42
Show file tree
Hide file tree
Showing 21 changed files with 155 additions and 52 deletions.
6 changes: 6 additions & 0 deletions apps/docs/content/guides/auth/auth-anonymous.mdx
Original file line number Diff line number Diff line change
Expand Up @@ -30,6 +30,12 @@ See the [Access control section](#access-control) for more details.

</Admonition>

<Admonition type="caution" label="Use Dynamic Rendering with Next.js">

The Supabase team has received reports of user metadata being cached across unique anonymous users as a result of Next.js static page rendering. For the best user experience, utilize dynamic page rendering.

</Admonition>

<Admonition type="note" label="Self hosting and local development">

For self-hosting, you can update your project configuration using the files and environment variables provided. See the [local development docs](/docs/guides/cli/config) for more details.
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -126,7 +126,7 @@ hideToc: true
```

```ts utils/supabase/server.ts
import { createServerClient, type CookieOptions } from '@supabase/ssr'
import { createServerClient } from '@supabase/ssr'
import { cookies } from 'next/headers'
export function createClient() {
Expand Down
2 changes: 1 addition & 1 deletion apps/docs/content/guides/platform/sso/azure.mdx
Original file line number Diff line number Diff line change
Expand Up @@ -83,7 +83,7 @@ Finally, click the _Save_ button to save the configuration.

## Step 7: Obtain metadata URL and send to Supabase [#send-metadata-url]

Supabase needs to finalize enabling single sign-on with your Azure AD application. To do this, copy and send the link under **App Federation Metadata Url** in \*section 3 **SAML Certificates\*** to your support contact and await further instructions. If you're not clear who to send this link to or need further assistance, reach out to [[email protected]](mailto:support@supabase.com).
Supabase needs to finalize enabling single sign-on with your Azure AD application. To do this, copy and send the link under **App Federation Metadata Url** in \*section 3 **SAML Certificates\*** to your support contact and await further instructions. If you're not clear who to send this link to or need further assistance, reach out to [Supabase Support](https://supabase.help).

**Do not test the login until you have heard back from the support contact.**

Expand Down
2 changes: 1 addition & 1 deletion apps/docs/content/guides/platform/sso/gsuite.mdx
Original file line number Diff line number Diff line change
Expand Up @@ -39,7 +39,7 @@ This is a very important step. Click on _DOWNLOAD METADATA_ and save the file th

![Google Workspace: Web and mobile apps admin console, Add custom SAML, Google Identity Provider details screen](/docs/img/sso-gsuite-step-04.png)

It's very important to send this file to your support contact at Supabase to complete the SSO setup process. If you're not sure where to send this file, you can always reach us at [[email protected]](mailto:support@supabase.com).
It's very important to send this file to your support contact at Supabase to complete the SSO setup process. If you're not sure where to send this file, you can always reach out to [Supabase Support](https://supabase.help).

**Important: Make sure the certificate as shown on screen has at least 1 year before it expires. Mark down this date in your calendar so you will be reminded that you need to update the certificate without any downtime for your users.**

Expand Down
2 changes: 1 addition & 1 deletion apps/docs/content/guides/platform/sso/okta.mdx
Original file line number Diff line number Diff line change
Expand Up @@ -67,7 +67,7 @@ Supabase needs to finalize enabling single sign-on with your Okta application.

To do this scroll down to the _SAML Signing Certificates_ section on the _Sign On_ tab of the _Supabase_ application. Pick the the _SHA-2_ row with an _Active_ status. Click on the _Actions_ dropdown button and then on the _View IdP Metadata_.

This will open up the SAML 2.0 Metadata XML file in a new tab in your browser. Copy this URL and send it to your support contact and await further instructions. If you're not clear who to send this link to or need further assistance, contact [[email protected]](mailto:support@supabase.com).
This will open up the SAML 2.0 Metadata XML file in a new tab in your browser. Copy this URL and send it to your support contact and await further instructions. If you're not clear who to send this link to or need further assistance, contact [Supabase Support](https://supabase.help).

The link usually has this structure: `https://<okta-org>.okta.com/apps/<app-id>/sso/saml/metadata`

Expand Down
2 changes: 1 addition & 1 deletion apps/studio/components/grid/SupabaseGrid.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -241,7 +241,7 @@ const SupabaseGridLayout = (props: SupabaseGridProps) => {
}, [state.table, props.table, props.schema])

return (
<div className="h-full flex flex-col">
<div className="sb-grid h-full flex flex-col">
<Header
table={props.table}
sorts={sorts}
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -1371,14 +1371,22 @@ const PROVIDER_SAML = {
SAML_EXTERNAL_URL: {
title: 'SAML metadata URL',
description:
'You may use a different SAML metadata URL from what is defined with the API External URL. Please validate that your SAML External URL can reach the Custom Domain or Project URL',
'You may use a different SAML metadata URL from what is defined with the API External URL. Please validate that your SAML External URL can reach the Custom Domain or Project URL.',
descriptionOptional: 'Optional',
type: 'string',
},
SAML_ALLOW_ENCRYPTED_ASSERTIONS: {
title: 'Allow encrypted SAML Assertions',
description:
'Some SAML Identity Providers require support for encrypted assertions. Usually this is not necessary.',
descriptionOptional: 'Optional',
type: 'boolean',
},
},
validationSchema: object().shape({
SAML_ENABLED: boolean().required(),
SAML_EXTERNAL_URL: string().matches(urlRegex, 'Must be a valid URL').optional(),
SAML_ALLOW_ENCRYPTED_ASSERTIONS: boolean().optional(),
}),
misc: {
iconKey: 'saml-icon',
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -32,6 +32,11 @@ const ExtensionCard = ({ extension }: ExtensionCardProps) => {

const X_PADDING = 'px-5'
const extensionMeta = extensions.find((item: any) => item.name === extension.name)
const docsUrl = extensionMeta?.link.startsWith('/guides')
? siteUrl === 'http://localhost:8082'
? `http://localhost:3001/docs${extensions.find((item) => item.name === extension.name)?.link}`
: `https://supabase.com/docs${extensions.find((item) => item.name === extension.name)?.link}`
: extensions.find((item: any) => item.name === extension.name)?.link ?? undefined

const { mutate: disableExtension, isLoading: isDisabling } = useDatabaseExtensionDisableMutation({
onSuccess: () => {
Expand Down Expand Up @@ -102,26 +107,18 @@ const ExtensionCard = ({ extension }: ExtensionCardProps) => {
</a>
</Button>
)}
<Button asChild type="default" icon={<Book />} className="rounded-full">
<a
target="_blank"
rel="noreferrer"
className="font-mono tracking-tighter"
href={
extensionMeta?.link.startsWith('/guides')
? siteUrl === 'http://localhost:8082'
? `http://localhost:3001/docs${
extensions.find((item) => item.name === extension.name)?.link
}`
: `https://supabase.com/docs${
extensions.find((item) => item.name === extension.name)?.link
}`
: extensions.find((item: any) => item.name === extension.name)?.link ?? ''
}
>
文档
</a>
</Button>
{docsUrl !== undefined && (
<Button asChild type="default" icon={<Book />} className="rounded-full">
<a
target="_blank"
rel="noreferrer"
className="font-mono tracking-tighter"
href={docsUrl}
>
文档
</a>
</Button>
)}
</div>
</div>

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -26,6 +26,9 @@ export const inferProjectStatus = (project: ProjectInfo) => {
case PROJECT_STATUS.RESTORE_FAILED:
status = 'isRestoreFailed'
break
case PROJECT_STATUS.UPGRADING:
status = 'isUpgrading'
break
case PROJECT_STATUS.UNKNOWN:
case PROJECT_STATUS.COMING_UP:
status = 'isComingUp'
Expand All @@ -43,4 +46,5 @@ export type InferredProjectStatus =
| 'isRestoring'
| 'isRestoreFailed'
| 'isComingUp'
| 'isUpgrading'
| undefined
Original file line number Diff line number Diff line change
Expand Up @@ -42,6 +42,7 @@ export const ProjectCardStatus = ({
if (projectStatus === 'isRestarting') return 'Project is restarting'
if (projectStatus === 'isComingUp') return 'Project is coming up'
if (projectStatus === 'isRestoring') return 'Project is restoring'
if (projectStatus === 'isUpgrading') return 'Project is upgrading'
if (projectStatus === 'isRestoreFailed') return 'Project restore failed'
if (projectStatus === 'isPauseFailed') return 'Project pause failed'

Expand All @@ -61,6 +62,7 @@ export const ProjectCardStatus = ({
if (projectStatus === 'isRestarting') return 'Your project will be ready in a few minutes'
if (projectStatus === 'isComingUp') return 'Your project will be ready in a few minutes'
if (projectStatus === 'isRestoring') return 'Your project will be ready in a few minutes'
if (projectStatus === 'isUpgrading') return 'Your project will be ready in a few minutes'
if (projectStatus === 'isRestoreFailed') return 'Please contact support for assistance'
if (projectStatus === 'isPauseFailed') return 'Please contact support for assistance'

Expand Down
18 changes: 12 additions & 6 deletions apps/studio/components/interfaces/SQLEditor/MoveQueryModal.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -65,17 +65,23 @@ export const MoveQueryModal = ({ visible, snippets = [], onClose }: MoveQueryMod

const { mutateAsync: createFolder, isLoading: isCreatingFolder } =
useSQLSnippetFolderCreateMutation()
const {
mutate: moveSnippet,
mutateAsync: moveSnippetAsync,
isLoading: isMovingSnippet,
} = useContentUpsertV2Mutation({
const { mutateAsync: moveSnippetAsync, isLoading: isMovingSnippet } = useContentUpsertV2Mutation({
onError: (error) => {
toast.error(`移动查询失败:${error.message}`)
},
})

const FormSchema = z.object({ name: z.string() })
const FormSchema = z
.object({ name: z.string().min(1, 'Please provide a name for the folder') })
.refine(
(data) => {
return !snapV2.allFolderNames.includes(data.name)
},
{
message: 'This folder name already exists',
path: ['name'],
}
)
const form = useForm<z.infer<typeof FormSchema>>({
mode: 'onSubmit',
reValidateMode: 'onSubmit',
Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -40,6 +40,7 @@ export const generateProductRoutes = (
project?: Project,
features?: { auth?: boolean; edgeFunctions?: boolean; storage?: boolean; realtime?: boolean }
): Route[] => {
const isProjectActive = project?.status === PROJECT_STATUS.ACTIVE_HEALTHY
const isProjectBuilding = project?.status === PROJECT_STATUS.COMING_UP
const buildingUrl = `/project/${ref}`

Expand All @@ -59,7 +60,13 @@ export const generateProductRoutes = (
key: 'database',
label: '数据库',
icon: <Database size={ICON_SIZE} strokeWidth={ICON_STROKE_WIDTH} />,
link: ref && (isProjectBuilding ? buildingUrl : `/project/${ref}/database/tables`),
link:
ref &&
(isProjectBuilding
? buildingUrl
: isProjectActive
? `/project/${ref}/database/tables`
: `/project/${ref}/database/backups/scheduled`),
},
...(storageEnabled
? [
Expand Down
17 changes: 12 additions & 5 deletions apps/studio/components/layouts/ProjectLayout/ProjectLayout.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -44,6 +44,7 @@ const routesToIgnoreProjectDetailsRequest = [
const routesToIgnoreDBConnection = [
'/project/[ref]/branches',
'/project/[ref]/database/backups/scheduled',
'/project/[ref]/database/backups/pitr',
'/project/[ref]/settings/addons',
]

Expand Down Expand Up @@ -89,6 +90,11 @@ const ProjectLayout = ({
const navLayoutV2 = useFlag('navigationLayoutV2')

const isPaused = selectedProject?.status === PROJECT_STATUS.INACTIVE
const showProductMenu = selectedProject
? selectedProject.status === PROJECT_STATUS.ACTIVE_HEALTHY ||
(selectedProject.status === PROJECT_STATUS.COMING_UP &&
router.pathname.includes('/project/[ref]/settings'))
: true
const ignorePausedState =
router.pathname === '/project/[ref]' || router.pathname.includes('/project/[ref]/settings')
const showPausedState = isPaused && !ignorePausedState
Expand Down Expand Up @@ -119,11 +125,11 @@ const ProjectLayout = ({
direction="horizontal"
autoSaveId="project-layout"
>
{!showPausedState && productMenu && (
{showProductMenu && productMenu && (
<>
<ResizablePanel
className={cn(resizableSidebar ? 'min-w-64 max-w-[32rem]' : 'min-w-64 max-w-64')}
defaultSize={1} // forces panel to smallest width possible, at w-64
defaultSize={0} // forces panel to smallest width possible, at w-64
>
<MenuBarWrapper
isLoading={isLoading}
Expand Down Expand Up @@ -221,6 +227,7 @@ const ContentWrapper = ({ isLoading, isBlocking = true, children }: ContentWrapp

const isSettingsPages = router.pathname.includes('/project/[ref]/settings')
const isVaultPage = router.pathname === '/project/[ref]/settings/vault'
const isBackupsPage = router.pathname.includes('/project/[ref]/database/backups')

const requiresDbConnection: boolean =
(!isSettingsPages && !routesToIgnoreDBConnection.includes(router.pathname)) || isVaultPage
Expand Down Expand Up @@ -248,11 +255,11 @@ const ContentWrapper = ({ isLoading, isBlocking = true, children }: ContentWrapp
return router.pathname.endsWith('[ref]') ? <LoadingState /> : <Loading />
}

if (isRestarting) {
if (isRestarting && !isBackupsPage) {
return <RestartingState />
}

if (isProjectUpgrading) {
if (isProjectUpgrading && !isBackupsPage) {
return <UpgradingState />
}

Expand All @@ -272,7 +279,7 @@ const ContentWrapper = ({ isLoading, isBlocking = true, children }: ContentWrapp
return <RestoringState />
}

if (isProjectRestoreFailed) {
if (isProjectRestoreFailed && !isBackupsPage) {
return <RestoreFailedState />
}

Expand Down
Original file line number Diff line number Diff line change
Expand Up @@ -531,8 +531,11 @@ export const SQLEditorNav = ({ searchText: _searchText }: SQLEditorNavProps) =>
onSelectShare={() => setSelectedSnippetToShare(element.metadata as Snippet)}
onEditSave={(name: string) => {
// [Joshen] Inline editing only for folders for now
if (name.length === 0) snapV2.removeFolder(element.id as string)
else snapV2.saveFolder({ id: element.id as string, name })
if (name.length === 0 && element.id === 'new-folder') {
snapV2.removeFolder(element.id as string)
} else if (name.length > 0) {
snapV2.saveFolder({ id: element.id as string, name })
}
}}
/>
)}
Expand Down
28 changes: 21 additions & 7 deletions apps/studio/pages/project/[ref]/database/backups/pitr.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -14,7 +14,10 @@ import { useBackupsQuery } from 'data/database/backups-query'
import { useOrgSubscriptionQuery } from 'data/subscriptions/org-subscription-query'
import { useCheckPermissions, usePermissionsLoaded } from 'hooks/misc/useCheckPermissions'
import { useSelectedOrganization } from 'hooks/misc/useSelectedOrganization'
import { PROJECT_STATUS } from 'lib/constants'
import { AlertCircle } from 'lucide-react'
import type { NextPageWithLayout } from 'types'
import { Alert_Shadcn_, AlertDescription_Shadcn_, AlertTitle_Shadcn_ } from 'ui'

const DatabasePhysicalBackups: NextPageWithLayout = () => {
const { project } = useProjectContext()
Expand Down Expand Up @@ -58,6 +61,7 @@ const PITR = () => {

const plan = subscription?.plan?.id
const isEnabled = backups?.pitr_enabled
const isActiveHealthy = project?.status === PROJECT_STATUS.ACTIVE_HEALTHY

const isPermissionsLoaded = usePermissionsLoaded()
const canReadPhysicalBackups = useCheckPermissions(PermissionAction.READ, 'physical_backups')
Expand All @@ -72,21 +76,31 @@ const PITR = () => {
{isError && <AlertError error={error} subject="Failed to retrieve PITR backups" />}
{isSuccess && (
<>
{isEnabled ? (
<>
<PITRNotice />
<PITRSelection />
</>
) : (
{!isEnabled ? (
<UpgradeToPro
addon="pitr"
primaryText="Point in Time Recovery is a Pro Plan add-on."
secondaryText={
plan === 'free'
? 'With PITR, you can roll back to a specific time (to the second!). PITR starts from $100/mo and is available for Pro Plan customers. Note that the Pro Plan already includes daily backups for no extra chargePITR is an optional upgrade.'
? 'With PITR, you can roll back to a specific time (to the second!). PITR starts from $100/mo and is available for Pro Plan customers. Note that the Pro Plan already includes daily backups for no extra chargePITR is an optional upgrade.'
: 'Please enable the add-on to enable point in time recovery for your project.'
}
/>
) : !isActiveHealthy ? (
<Alert_Shadcn_>
<AlertCircle />
<AlertTitle_Shadcn_>
Point in Time Recovery is not available while project is offline
</AlertTitle_Shadcn_>
<AlertDescription_Shadcn_>
Your project needs to be online to restore your database with Point in Time Recovery
</AlertDescription_Shadcn_>
</Alert_Shadcn_>
) : (
<>
<PITRNotice />
<PITRSelection />
</>
)}
</>
)}
Expand Down
2 changes: 1 addition & 1 deletion apps/studio/pages/project/[ref]/database/tables/[id].tsx
Original file line number Diff line number Diff line change
@@ -1,4 +1,5 @@
import type { PostgresTable } from '@supabase/postgres-meta'
import { ChevronRight } from 'lucide-react'

import { useParams } from 'common'
import { ColumnList } from 'components/interfaces/Database'
Expand All @@ -8,7 +9,6 @@ import DatabaseLayout from 'components/layouts/DatabaseLayout/DatabaseLayout'
import { ScaffoldContainer, ScaffoldSection } from 'components/layouts/Scaffold'
import { FormHeader } from 'components/ui/Forms/FormHeader'
import useTable from 'hooks/misc/useTable'
import { ChevronRight } from 'lucide-react'
import { useTableEditorStateSnapshot } from 'state/table-editor'
import type { NextPageWithLayout } from 'types'
import ShimmeringLoader from 'ui-patterns/ShimmeringLoader'
Expand Down
2 changes: 0 additions & 2 deletions apps/studio/pages/project/[ref]/database/tables/index.tsx
Original file line number Diff line number Diff line change
@@ -1,6 +1,5 @@
import { useState } from 'react'

import { useQueryClient } from '@tanstack/react-query'
import { TableList } from 'components/interfaces/Database'
import { SidePanelEditor } from 'components/interfaces/TableGridEditor'
import DeleteConfirmationDialogs from 'components/interfaces/TableGridEditor/DeleteConfirmationDialogs'
Expand All @@ -12,7 +11,6 @@ import { useTableEditorStateSnapshot } from 'state/table-editor'
import type { NextPageWithLayout } from 'types'

const DatabaseTables: NextPageWithLayout = () => {
const queryClient = useQueryClient()
const snap = useTableEditorStateSnapshot()
const [selectedTableToEdit, setSelectedTableToEdit] = useState<Table>()

Expand Down
2 changes: 1 addition & 1 deletion apps/studio/pages/project/[ref]/index.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -52,7 +52,7 @@ const Home: NextPageWithLayout = () => {
/>
</div>
<div className="flex items-center gap-x-3">
<SecurityStatus />
{project?.status === PROJECT_STATUS.ACTIVE_HEALTHY && <SecurityStatus />}
{IS_PLATFORM && project?.status === PROJECT_STATUS.ACTIVE_HEALTHY && <ServiceStatus />}
{IS_PLATFORM && project?.status === PROJECT_STATUS.ACTIVE_HEALTHY && <Connect />}
</div>
Expand Down
Loading

0 comments on commit c1b2b42

Please sign in to comment.