updated compute form. moved warning panels. added collapsible for advanced options

This commit is contained in:
Jonathan Summers-Muir committed 2024-10-25 00:12:38 +08:00
1 parent 6afbd65182
commit be9ba1c488
5 files changed
+664 -547

No files matched your search

@@ -0,0 +1,64 @@
import { ScaffoldContainer } from 'components/layouts/Scaffold'
import { Form_Shadcn_, Separator, Skeleton } from 'ui'
import { FormItemLayout } from 'ui-patterns/form/FormItemLayout/FormItemLayout'
export function DiskManagementFormLoading() {
return (
<Form_Shadcn_>
<form className="flex flex-col gap-8">
<ScaffoldContainer className="relative flex flex-col gap-10" bottomPadding>
<Separator />
<FormItemLayout
label="Compute size"
layout="horizontal"
isReactForm={false}
labelOptional={<p>Hardware resources allocated to your postgres database</p>}
>
<div className="grid grid-cols-3 flex-wrap gap-3">
<Skeleton className="bg-surface-300 block w-full h-[110px]" />
<Skeleton className="bg-surface-300 block w-full h-[110px]" />
<Skeleton className="bg-surface-300 block w-full h-[110px]" />
<Skeleton className="bg-surface-300 block w-full h-[110px]" />
<Skeleton className="bg-surface-300 block w-full h-[110px]" />
<Skeleton className="bg-surface-300 block w-full h-[110px]" />
<Skeleton className="bg-surface-300 block w-full h-[110px]" />
<Skeleton className="bg-surface-300 block w-full h-[110px]" />
<Skeleton className="bg-surface-300 block w-full h-[110px]" />
<Skeleton className="bg-surface-300 block w-full h-[110px]" />
</div>
</FormItemLayout>
<Separator />
<FormItemLayout label="Storage type" layout="horizontal" isReactForm={false}>
<div className="grid grid-cols-2 flex-wrap gap-3">
<Skeleton className="bg-surface-300 block w-full h-21" />
<Skeleton className="bg-surface-300 block w-full h-21" />
</div>
</FormItemLayout>
{/* <FormItemLayout
label="Compute size"
layout="horizontal"
isReactForm={false}
labelOptional="hardware resources allocated to your postgres database"
>
<Skeleton className="bg-surface-300 w-100 h-12" />
<Skeleton className="bg-surface-300 w-100 h-12" />
<Skeleton className="bg-surface-300 w-100 h-12" />
</FormItemLayout>
<FormItemLayout
label="Compute size"
layout="horizontal"
isReactForm={false}
labelOptional="hardware resources allocated to your postgres database"
>
<Skeleton className="bg-surface-300 w-100 h-10" />
</FormItemLayout> */}
</ScaffoldContainer>
</form>
</Form_Shadcn_>
)
}
@@ -5,25 +5,35 @@ import { Card, CardContent } from 'ui'
import CountdownTimerRadial from '../../ui/CountdownTimer/CountdownTimerRadial'
import CountdownTimerSpan from '../../ui/CountdownTimer/CountdownTimerSpan'
export function DiskCountdownRadial({ remainingTime }: { remainingTime: number }) {
export function DiskCountdownRadial({
remainingTime,
show = true,
}: {
remainingTime: number
show?: boolean
}) {
const progressPercentage = (remainingTime / COOLDOWN_DURATION) * 100
return (
<AnimatePresence>
{remainingTime !== 0 && (
{remainingTime !== 0 && show && (
<motion.div
initial={{ opacity: 0, height: 0 }}
animate={{ opacity: 1, height: 'auto' }}
exit={{ opacity: 0, height: 0 }}
transition={{ duration: 0.2 }}
>
<Card className="px-2 rounded-none">
<Card className="px-2 rounded bg-surface-100">
<CardContent className="py-3 flex gap-3 px-3 items-center">
<CountdownTimerRadial progress={progressPercentage} />
<div className="flex flex-col">
<p className="text-foreground-lighter text-sm p-0">
<p className="text-foreground text-sm p-0">
6-hour wait period between disk modifications
</p>
<p className="text-foreground-lighter text-sm p-0">
You can't modify your disk configuration until the 6-hour cool down period ends.
You can however change the compute size..
</p>
<CountdownTimerSpan seconds={remainingTime} />
</div>
</CardContent>
File diff suppressed because it is too large. Load diff
@@ -13,94 +13,104 @@ const baseSchema = z.object({
computeSize: z.string().describe('Compute size'),
})
export const DiskStorageSchema = baseSchema.superRefine((data, ctx) => {
const { storageType, totalSize, provisionedIOPS, throughput, computeSize } = data
export const CreateDiskStorageSchema = (defaultTotalSize: number) => {
const schema = baseSchema.superRefine((data, ctx) => {
const { storageType, totalSize, provisionedIOPS, throughput, computeSize } = data
// if(computeSize)
if (storageType === 'io2') {
// Validation rules for io2
const maxIOPS = calculateMaxIopsAllowed(totalSize)
if (provisionedIOPS < 100) {
if (totalSize < defaultTotalSize) {
ctx.addIssue({
code: z.ZodIssueCode.custom,
message: 'Provisioned IOPS must be at least 100',
path: ['provisionedIOPS'],
})
} else if (provisionedIOPS > maxIOPS) {
if (totalSize >= 8) {
ctx.addIssue({
code: z.ZodIssueCode.custom,
message: `Provisioned IOPS must be at most ${maxIOPS}.`,
path: ['provisionedIOPS'],
})
} else {
ctx.addIssue({
code: z.ZodIssueCode.custom,
message: `Invalid IOPS value due to small disk size`,
path: ['provisionedIOPS'],
})
}
}
if (throughput !== undefined) {
ctx.addIssue({
code: z.ZodIssueCode.custom,
message: 'Throughput is not configurable for io2.',
path: ['throughput'],
})
}
if (totalSize > DISK_LIMITS[DiskType.IO2].maxStorage) {
ctx.addIssue({
code: z.ZodIssueCode.custom,
message: 'Allocated disksize must not exceed 61,440 GB',
message: `Allocated disk size must be at least ${defaultTotalSize} GB.`,
path: ['totalSize'],
})
}
} else if (storageType === 'gp3') {
// Validation rules for gp3
const maxIOPS = Math.min(500 * totalSize, 16000)
const maxThroughput = Math.min(0.25 * provisionedIOPS, 1000)
if (provisionedIOPS < 3000) {
ctx.addIssue({
code: z.ZodIssueCode.custom,
message: `Provisioned IOPS must be at least 3000`,
path: ['provisionedIOPS'],
})
} else if (provisionedIOPS > maxIOPS) {
if (totalSize >= 8) {
if (storageType === 'io2') {
// Validation rules for io2
const maxIOPS = calculateMaxIopsAllowed(totalSize)
if (provisionedIOPS < 100) {
ctx.addIssue({
code: z.ZodIssueCode.custom,
message: `Provisioned IOPS must be at most ${maxIOPS}`,
message: 'Provisioned IOPS must be at least 100',
path: ['provisionedIOPS'],
})
} else {
} else if (provisionedIOPS > maxIOPS) {
if (totalSize >= 8) {
ctx.addIssue({
code: z.ZodIssueCode.custom,
message: `Provisioned IOPS must be at most ${maxIOPS}.`,
path: ['provisionedIOPS'],
})
} else {
ctx.addIssue({
code: z.ZodIssueCode.custom,
message: `Invalid IOPS value due to small disk size`,
path: ['provisionedIOPS'],
})
}
}
if (throughput !== undefined) {
ctx.addIssue({
code: z.ZodIssueCode.custom,
message: `Invalid IOPS value due to invalid disk size`,
message: 'Throughput is not configurable for io2.',
path: ['throughput'],
})
}
if (totalSize > DISK_LIMITS[DiskType.IO2].maxStorage) {
ctx.addIssue({
code: z.ZodIssueCode.custom,
message: 'Allocated disksize must not exceed 61,440 GB',
path: ['totalSize'],
})
}
} else if (storageType === 'gp3') {
// Validation rules for gp3
const maxIOPS = Math.min(500 * totalSize, 16000)
const maxThroughput = Math.min(0.25 * provisionedIOPS, 1000)
if (provisionedIOPS < 3000) {
ctx.addIssue({
code: z.ZodIssueCode.custom,
message: `Provisioned IOPS must be at least 3000`,
path: ['provisionedIOPS'],
})
} else if (provisionedIOPS > maxIOPS) {
if (totalSize >= 8) {
ctx.addIssue({
code: z.ZodIssueCode.custom,
message: `Provisioned IOPS must be at most ${maxIOPS}`,
path: ['provisionedIOPS'],
})
} else {
ctx.addIssue({
code: z.ZodIssueCode.custom,
message: `Invalid IOPS value due to invalid disk size`,
path: ['provisionedIOPS'],
})
}
}
if (throughput !== undefined && (throughput < 125 || throughput > maxThroughput)) {
ctx.addIssue({
code: z.ZodIssueCode.custom,
message: `Throughput must be set between 125 and ${maxThroughput?.toLocaleString()} MB/s.`,
path: ['throughput'],
})
}
if (totalSize > DISK_LIMITS[DiskType.GP3].maxStorage) {
ctx.addIssue({
code: z.ZodIssueCode.custom,
message: 'Allocated disksize must not exceed 16,384 GB',
path: ['totalSize'],
})
}
}
})
if (throughput !== undefined && (throughput < 125 || throughput > maxThroughput)) {
ctx.addIssue({
code: z.ZodIssueCode.custom,
message: `Throughput must be set between 125 and ${maxThroughput?.toLocaleString()} MB/s.`,
path: ['throughput'],
})
}
if (totalSize > DISK_LIMITS[DiskType.GP3].maxStorage) {
ctx.addIssue({
code: z.ZodIssueCode.custom,
message: 'Allocated disksize must not exceed 16,384 GB',
path: ['totalSize'],
})
}
}
})
return schema
}
export type DiskStorageSchemaType = z.infer<typeof DiskStorageSchema>
export type DiskStorageSchemaType = z.infer<ReturnType<typeof CreateDiskStorageSchema>>
@@ -115,7 +115,7 @@ interface DiskSizeMeterProps {
form: UseFormReturn<DiskStorageSchemaType>
numReplicas: number
isDialogOpen: boolean
isWithinCooldown: boolean
disabled?: boolean
setIsDialogOpen: (isOpen: boolean) => void
onSubmit: (values: DiskStorageSchemaType) => Promise<void>
}
@@ -123,7 +123,7 @@ interface DiskSizeMeterProps {
export const DiskManagementReviewAndSubmitDialog = ({
isDialogOpen,
setIsDialogOpen,
isWithinCooldown,
disabled,
form,
numReplicas,
loading,
@@ -205,14 +205,14 @@ export const DiskManagementReviewAndSubmitDialog = ({
const isValid = await form.trigger()
if (isValid) setIsDialogOpen(true)
}}
disabled={isWithinCooldown || !isDirty}
disabled={disabled || !isDirty}
tooltip={{
content: {
side: 'bottom',
text: !canUpdateDiskConfiguration
? 'You need additional permissions to update disk configuration'
: isWithinCooldown
? 'Currently within cooldown period from previous disk change'
: disabled
? 'Current form values are invalid'
: undefined,
},
}}