refactor: change edit style and logic, create new MonitorPicker component

This commit is contained in:
moonrailgun 2024-09-16 17:08:58 +08:00
parent ed2141af22
commit 72a1e7b024
5 changed files with 116 additions and 49 deletions

View File

@ -1,12 +1,23 @@
import { Select, SelectProps } from 'antd';
import { Select as AntdSelect, SelectProps as AntdSelectProps } from 'antd';
import React from 'react';
import { trpc } from '../../api/trpc';
import { useCurrentWorkspaceId } from '../../store/user';
import { ColorTag } from '../ColorTag';
import { useTranslation } from '@i18next-toolkit/react';
import {
Select,
SelectContent,
SelectItem,
SelectTrigger,
SelectValue,
} from '../ui/select';
import { PropsOf } from '@/utils/type';
interface MonitorPickerProps extends SelectProps<string> {}
export const MonitorPicker: React.FC<MonitorPickerProps> = React.memo(
interface MonitorPickerOldProps extends AntdSelectProps<string> {}
/**
* @deprecated please use MonitorPicker
*/
export const MonitorPickerOld: React.FC<MonitorPickerOldProps> = React.memo(
(props) => {
const { t } = useTranslation();
const workspaceId = useCurrentWorkspaceId();
@ -15,13 +26,40 @@ export const MonitorPicker: React.FC<MonitorPickerProps> = React.memo(
});
return (
<Select placeholder={t('Select monitor')} {...props}>
<AntdSelect placeholder={t('Select monitor')} {...props}>
{allMonitor.map((m) => (
<Select.Option key={m.id} value={m.id}>
<AntdSelect.Option key={m.id} value={m.id}>
<ColorTag label={m.type} />
{m.name}
</Select.Option>
</AntdSelect.Option>
))}
</AntdSelect>
);
}
);
MonitorPickerOld.displayName = 'MonitorPickerOld';
export const MonitorPicker: React.FC<PropsOf<typeof Select>> = React.memo(
(props) => {
const { t } = useTranslation();
const workspaceId = useCurrentWorkspaceId();
const { data: allMonitor = [] } = trpc.monitor.all.useQuery({
workspaceId,
});
return (
<Select {...props}>
<SelectTrigger>
<SelectValue placeholder={t('Select monitor')} />
</SelectTrigger>
<SelectContent>
{allMonitor.map((m) => (
<SelectItem key={m.id} value={m.id}>
<ColorTag label={m.type} />
{m.name}
</SelectItem>
))}
</SelectContent>
</Select>
);
}

View File

@ -1,5 +1,5 @@
import React from 'react';
import { MonitorPicker } from '../MonitorPicker';
import { MonitorPicker, MonitorPickerOld } from '../MonitorPicker';
import { useTranslation } from '@i18next-toolkit/react';
import { Button } from '@/components/ui/button';
import { LuMinusCircle, LuPlus } from 'react-icons/lu';
@ -23,6 +23,17 @@ import { domainRegex, slugRegex } from '@tianji/shared';
import { useElementSize } from '@/hooks/useResizeObserver';
import { Switch } from '@/components/ui/switch';
import { Separator } from '@/components/ui/separator';
import {
Select,
SelectContent,
SelectItem,
SelectTrigger,
SelectValue,
} from '@/components/ui/select';
import { ColorTag } from '@/components/ColorTag';
import { Collapsible, CollapsibleContent } from '@/components/ui/collapsible';
import { CollapsibleTrigger } from '@radix-ui/react-collapsible';
import { CaretSortIcon } from '@radix-ui/react-icons';
const Text = Typography.Text;
@ -135,42 +146,50 @@ export const MonitorStatusPageEditForm: React.FC<MonitorStatusPageEditFormProps>
)}
/>
{/* Description */}
<FormField
control={form.control}
name="description"
render={({ field }) => (
<FormItem>
<FormLabel optional={true}>{t('Description')}</FormLabel>
<FormControl>
<MarkdownEditorFormItem {...field} />
</FormControl>
<FormMessage />
</FormItem>
)}
/>
<Collapsible>
<CollapsibleTrigger className="flex w-full items-center justify-between">
<span className="text-sm">{t('Advanced')}</span>
<CaretSortIcon className="h-4 w-4" />
</CollapsibleTrigger>
<CollapsibleContent>
{/* Description */}
<FormField
control={form.control}
name="description"
render={({ field }) => (
<FormItem>
<FormLabel optional={true}>{t('Description')}</FormLabel>
<FormControl>
<MarkdownEditorFormItem {...field} />
</FormControl>
<FormMessage />
</FormItem>
)}
/>
{/* Custom Domain */}
<FormField
control={form.control}
name="domain"
render={({ field }) => (
<FormItem>
<FormLabel optional={true}>{t('Custom Domain')}</FormLabel>
<FormControl>
<Input {...field} />
</FormControl>
<FormDescription>
<div>
{t(
'You can config your status page in your own domain, for example: status.example.com'
)}
</div>
</FormDescription>
<FormMessage />
</FormItem>
)}
/>
{/* Custom Domain */}
<FormField
control={form.control}
name="domain"
render={({ field }) => (
<FormItem>
<FormLabel optional={true}>{t('Custom Domain')}</FormLabel>
<FormControl>
<Input {...field} />
</FormControl>
<FormDescription>
<div>
{t(
'You can config your status page in your own domain, for example: status.example.com'
)}
</div>
</FormDescription>
<FormMessage />
</FormItem>
)}
/>
</CollapsibleContent>
</Collapsible>
{/* MonitorList */}
<FormField
@ -181,13 +200,19 @@ export const MonitorStatusPageEditForm: React.FC<MonitorStatusPageEditFormProps>
<FormLabel>{t('Monitor List')}</FormLabel>
{fields.map((field, i) => (
<>
{i !== 0 && <Separator className="my-0.5" />}
{i !== 0 && <Separator />}
<div key={field.key} className="mb-2 flex flex-col gap-1">
<div key={field.key} className="mb-2 flex flex-col gap-2">
<Controller
control={form.control}
name={`monitorList.${i}.id`}
render={({ field }) => <MonitorPicker {...field} />}
render={({ field }) => (
<MonitorPicker
{...field}
value={field.value}
onValueChange={field.onChange}
/>
)}
/>
<div className="flex flex-1 items-center">
@ -214,6 +239,7 @@ export const MonitorStatusPageEditForm: React.FC<MonitorStatusPageEditFormProps>
</div>
</>
))}
<FormMessage />
<Button

View File

@ -6,7 +6,7 @@ import { useCurrentWorkspaceId } from '../../store/user';
import { ErrorTip } from '../ErrorTip';
import { Loading } from '../Loading';
import { NoWorkspaceTip } from '../NoWorkspaceTip';
import { MonitorPicker } from '../monitor/MonitorPicker';
import { MonitorPickerOld } from '../monitor/MonitorPicker';
import {
defaultErrorHandler,
defaultSuccessHandler,
@ -141,7 +141,7 @@ export const WebsiteConfig: React.FC<{ websiteId: string }> = React.memo(
'You can bind a monitor which will display health status in website overview'
)}
>
<MonitorPicker size="large" allowClear={true} />
<MonitorPickerOld size="large" allowClear={true} />
</Form.Item>
<Form.Item>

View File

@ -7,7 +7,7 @@ import { useCurrentWorkspaceId } from '../../store/user';
import { ErrorTip } from '../ErrorTip';
import { Loading } from '../Loading';
import { NoWorkspaceTip } from '../NoWorkspaceTip';
import { MonitorPicker } from '../monitor/MonitorPicker';
import { MonitorPickerOld } from '../monitor/MonitorPicker';
import {
defaultErrorHandler,
defaultSuccessHandler,
@ -126,7 +126,7 @@ export const WebsiteInfo: React.FC = React.memo(() => {
'You can bind a monitor which will display health status in website overview'
)}
>
<MonitorPicker size="large" allowClear={true} />
<MonitorPickerOld size="large" allowClear={true} />
</Form.Item>
<Form.Item>

3
src/client/utils/type.ts Normal file
View File

@ -0,0 +1,3 @@
import React from 'react';
export type PropsOf<T> = T extends React.ComponentType<infer P> ? P : never;