| 123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189190191192193194195196 |
- import { useParams } from 'common'
- import { UseFormReturn } from 'react-hook-form'
- import {
- FormControl,
- FormField,
- FormInputGroupInput,
- InputGroup,
- InputGroupAddon,
- InputGroupText,
- } from 'ui'
- import { Admonition } from 'ui-patterns'
- import { FormItemLayout } from 'ui-patterns/form/FormItemLayout/FormItemLayout'
- import { DiskStorageSchemaType } from '../DiskManagement.schema'
- import { DISK_AUTOSCALE_CONFIG_DEFAULTS } from '../ui/DiskManagement.constants'
- import { useDiskAutoscaleCustomConfigQuery } from '@/data/config/disk-autoscale-config-query'
- type AutoScaleFieldProps = {
- form: UseFormReturn<DiskStorageSchemaType>
- }
- export const AutoScaleFields = ({ form }: AutoScaleFieldProps) => {
- const { ref: projectRef } = useParams()
- const {
- control,
- setValue,
- formState: { errors },
- } = form
- const { totalSize, growthPercent, maxSizeGb, minIncrementGb } = form.watch()
- const { isError } = useDiskAutoscaleCustomConfigQuery({ projectRef })
- const _growthPercent = growthPercent ?? DISK_AUTOSCALE_CONFIG_DEFAULTS.growthPercent
- const _minIncrementGb = minIncrementGb ?? DISK_AUTOSCALE_CONFIG_DEFAULTS.minIncrementSize
- const _maxSizeGb = errors.maxSizeGb
- ? DISK_AUTOSCALE_CONFIG_DEFAULTS.maxSizeGb
- : (maxSizeGb ?? DISK_AUTOSCALE_CONFIG_DEFAULTS.maxSizeGb)
- const growthSize = Math.floor(totalSize * (_growthPercent / 100))
- const autoscaleGrowValue = Math.min(
- Math.max(Math.floor((totalSize * _growthPercent) / 100), _minIncrementGb),
- 200
- )
- const totalSizeAfterGrowth = Math.max(autoscaleGrowValue + totalSize, 8)
- const formattedTotalSizeAfterGrowth =
- totalSizeAfterGrowth < _maxSizeGb ? totalSizeAfterGrowth : _maxSizeGb
- const formattedGrowValue = formattedTotalSizeAfterGrowth - totalSize
- return (
- <>
- <FormField
- name="growthPercent"
- control={control}
- render={({ field }) => {
- return (
- <FormItemLayout
- layout="horizontal"
- label="Autoscale growth percent"
- id={field.name}
- labelOptional="Percentage of current disk size to grow"
- description={
- !errors.growthPercent
- ? `This amounts to ${growthSize} GB based on the current disk size of ${totalSize} GB`
- : undefined
- }
- className="[&>div>span]:text-foreground-lighter"
- >
- <FormControl className="max-w-20">
- <InputGroup>
- <FormInputGroupInput
- {...field}
- type="number"
- value={field.value ?? undefined}
- disabled={isError}
- onChange={(e) => {
- setValue(
- 'growthPercent',
- e.target.value === '' ? null : e.target.valueAsNumber,
- {
- shouldDirty: true,
- shouldValidate: true,
- }
- )
- }}
- placeholder={String(DISK_AUTOSCALE_CONFIG_DEFAULTS.growthPercent)}
- />
- <InputGroupAddon align="inline-end">
- <InputGroupText>%</InputGroupText>
- </InputGroupAddon>
- </InputGroup>
- </FormControl>
- </FormItemLayout>
- )
- }}
- />
- <FormField
- name="minIncrementGb"
- control={control}
- render={({ field }) => {
- return (
- <FormItemLayout
- layout="horizontal"
- label="Minimum increment"
- id={field.name}
- labelOptional="Minimum value to autoscale disk size by"
- description={
- !!minIncrementGb && minIncrementGb > growthSize && !errors.minIncrementGb
- ? `This value takes precedence as the minimum increment is larger than the growth percent`
- : undefined
- }
- className="[&>div>span]:text-foreground-lighter"
- >
- <FormControl className="max-w-32">
- <InputGroup>
- <FormInputGroupInput
- {...field}
- type="number"
- value={field.value ?? undefined}
- disabled={isError}
- onChange={(e) => {
- setValue(
- 'minIncrementGb',
- e.target.value === '' ? null : e.target.valueAsNumber,
- {
- shouldDirty: true,
- shouldValidate: true,
- }
- )
- }}
- placeholder={String(DISK_AUTOSCALE_CONFIG_DEFAULTS.minIncrementSize)}
- />
- <InputGroupAddon align="inline-end">
- <InputGroupText>GB</InputGroupText>
- </InputGroupAddon>
- </InputGroup>
- </FormControl>
- </FormItemLayout>
- )
- }}
- />
- <FormField
- name="maxSizeGb"
- control={control}
- render={({ field }) => {
- return (
- <FormItemLayout
- layout="horizontal"
- label="Maximum disk size"
- id={field.name}
- labelOptional="Maximum size that the disk can grow to"
- className="[&>div>span]:text-foreground-lighter"
- >
- <FormControl className="max-w-32">
- <InputGroup>
- <FormInputGroupInput
- {...field}
- type="number"
- value={field.value ?? undefined}
- disabled={isError}
- onChange={(e) => {
- setValue('maxSizeGb', e.target.value === '' ? null : e.target.valueAsNumber, {
- shouldDirty: true,
- shouldValidate: true,
- })
- }}
- placeholder={String(DISK_AUTOSCALE_CONFIG_DEFAULTS.maxSizeGb)}
- />
- <InputGroupAddon align="inline-end">
- <InputGroupText>GB</InputGroupText>
- </InputGroupAddon>
- </InputGroup>
- </FormControl>
- </FormItemLayout>
- )
- }}
- />
- {
- <Admonition type="default" showIcon={false} className="[&>div]:text-foreground-light">
- Disk size will automatically be expanded by{' '}
- <span className="text-foreground">
- {String(formattedGrowValue).length > 4
- ? formattedGrowValue.toFixed(2)
- : formattedGrowValue}{' '}
- GB
- </span>{' '}
- to a total of <span className="text-foreground">{formattedTotalSizeAfterGrowth} GB</span>{' '}
- when the database reaches 90% of the disk size
- </Admonition>
- }
- </>
- )
- }
|