| @@ -1,25 +0,0 @@ | |||
| /* | |||
| * @Author: 赵伟 | |||
| * @Date: 2024-04-28 14:18:11 | |||
| * @Description: 自定义 Table 单元格,没有数据时展示 -- | |||
| */ | |||
| import { Tooltip } from 'antd'; | |||
| function renderCell(text?: any | null) { | |||
| return <span>{text ?? '--'}</span>; | |||
| } | |||
| function CommonTableCell(ellipsis: boolean = false) { | |||
| if (ellipsis) { | |||
| return (text?: any | null) => ( | |||
| <Tooltip title={text} placement="topLeft" overlayStyle={{ maxWidth: '400px' }}> | |||
| {renderCell(text)} | |||
| </Tooltip> | |||
| ); | |||
| } else { | |||
| return renderCell; | |||
| } | |||
| } | |||
| export default CommonTableCell; | |||
| @@ -1,20 +0,0 @@ | |||
| /* | |||
| * @Author: 赵伟 | |||
| * @Date: 2024-04-28 14:18:11 | |||
| * @Description: 自定义 Table 日期类单元格 | |||
| */ | |||
| import { formatDate } from '@/utils/date'; | |||
| import dayjs from 'dayjs'; | |||
| function DateTableCell(text?: string | null) { | |||
| if (text === undefined || text === null || text === '') { | |||
| return <span>--</span>; | |||
| } | |||
| if (!dayjs(text).isValid()) { | |||
| return <span>无效的日期</span>; | |||
| } | |||
| return <span>{formatDate(text)}</span>; | |||
| } | |||
| export default DateTableCell; | |||
| @@ -1,5 +1,3 @@ | |||
| import CommonTableCell from '@/components/CommonTableCell'; | |||
| import DateTableCell from '@/components/DateTableCell'; | |||
| import KFIcon from '@/components/KFIcon'; | |||
| import { | |||
| ResourceData, | |||
| @@ -8,7 +6,8 @@ import { | |||
| resourceConfig, | |||
| } from '@/pages/Dataset/config'; | |||
| import { downLoadZip } from '@/utils/downloadfile'; | |||
| import { Button, Flex, Table } from 'antd'; | |||
| import tableCellRender, { TableCellValueType } from '@/utils/table'; | |||
| import { Button, Flex, Table, TableProps } from 'antd'; | |||
| import styles from './index.less'; | |||
| type ResourceVersionProps = { | |||
| @@ -38,37 +37,33 @@ function ResourceVersion({ resourceType, info }: ResourceVersionProps) { | |||
| downLoadZip(url, { url: record.url }); | |||
| }; | |||
| const columns = [ | |||
| const columns: TableProps<ResourceFileData>['columns'] = [ | |||
| { | |||
| title: '序号', | |||
| dataIndex: 'index', | |||
| key: 'index', | |||
| width: 80, | |||
| render(_text: string, _record: ResourceFileData, index: number) { | |||
| return <span>{index + 1}</span>; | |||
| }, | |||
| render: tableCellRender(false, TableCellValueType.Index), | |||
| }, | |||
| { | |||
| title: '文件名称', | |||
| dataIndex: 'file_name', | |||
| key: 'file_name', | |||
| render: (text: string, record: ResourceFileData) => ( | |||
| <a className="kf-table-row-link" onClick={() => downloadAlone(record)}> | |||
| {text} | |||
| </a> | |||
| ), | |||
| render: tableCellRender(false, TableCellValueType.Link, { | |||
| onClick: downloadAlone, | |||
| }), | |||
| }, | |||
| { | |||
| title: '文件大小', | |||
| dataIndex: 'file_size', | |||
| key: 'file_size', | |||
| render: CommonTableCell(), | |||
| render: tableCellRender(), | |||
| }, | |||
| { | |||
| title: '更新时间', | |||
| dataIndex: 'update_time', | |||
| key: 'update_time', | |||
| render: DateTableCell, | |||
| render: tableCellRender(false, TableCellValueType.Date), | |||
| }, | |||
| { | |||
| title: '操作', | |||
| @@ -4,8 +4,6 @@ | |||
| * @Description: 开发环境列表 | |||
| */ | |||
| import CommonTableCell from '@/components/CommonTableCell'; | |||
| import DateTableCell from '@/components/DateTableCell'; | |||
| import KFIcon from '@/components/KFIcon'; | |||
| import { DevEditorStatus } from '@/enums'; | |||
| import { useCacheState } from '@/hooks/pageCacheState'; | |||
| @@ -19,6 +17,7 @@ import themes from '@/styles/theme.less'; | |||
| import { openAntdModal } from '@/utils/modal'; | |||
| import { to } from '@/utils/promise'; | |||
| import SessionStorage from '@/utils/sessionStorage'; | |||
| import tableCellRender, { TableCellValueType } from '@/utils/table'; | |||
| import { modalConfirm } from '@/utils/ui'; | |||
| import { useNavigate } from '@umijs/max'; | |||
| import { | |||
| @@ -153,7 +152,7 @@ function EditorList() { | |||
| }; | |||
| // 分页切换 | |||
| const handleTableChange: TableProps['onChange'] = (pagination, filters, sorter, { action }) => { | |||
| const handleTableChange: TableProps['onChange'] = (pagination, _filters, _sorter, { action }) => { | |||
| if (action === 'paginate') { | |||
| setPagination(pagination); | |||
| } | |||
| @@ -186,21 +185,21 @@ function EditorList() { | |||
| dataIndex: 'computing_resource', | |||
| key: 'computing_resource', | |||
| width: '20%', | |||
| render: CommonTableCell(), | |||
| render: tableCellRender(), | |||
| }, | |||
| { | |||
| title: '创建者', | |||
| dataIndex: 'update_by', | |||
| key: 'update_by', | |||
| width: '20%', | |||
| render: CommonTableCell(), | |||
| render: tableCellRender(), | |||
| }, | |||
| { | |||
| title: '创建时间', | |||
| dataIndex: 'create_time', | |||
| key: 'create_time', | |||
| width: '20%', | |||
| render: DateTableCell, | |||
| render: tableCellRender(false, TableCellValueType.Date), | |||
| }, | |||
| { | |||
| title: '操作', | |||
| @@ -5,7 +5,7 @@ import { | |||
| getExpTrainInfosReq, | |||
| } from '@/services/experiment'; | |||
| import { to } from '@/utils/promise'; | |||
| import tableCellRender, { arrayFormatter, dateFormatter } from '@/utils/table'; | |||
| import tableCellRender, { TableCellValueType } from '@/utils/table'; | |||
| import { useSearchParams } from '@umijs/max'; | |||
| import { App, Button, Table, /* TablePaginationConfig,*/ TableProps, Tooltip } from 'antd'; | |||
| import classNames from 'classnames'; | |||
| @@ -23,7 +23,7 @@ type TableData = { | |||
| metrics_names: string[]; | |||
| metrics: Record<string, number>; | |||
| params_names: string[]; | |||
| params: Record<string, string>; | |||
| params: Record<string, number>; | |||
| }; | |||
| function ExperimentComparison() { | |||
| @@ -98,11 +98,12 @@ function ExperimentComparison() { | |||
| }, | |||
| }; | |||
| const columns: TableProps['columns'] = useMemo(() => { | |||
| const columns: TableProps<TableData>['columns'] = useMemo(() => { | |||
| const first: TableData | undefined = tableData[0]; | |||
| return [ | |||
| { | |||
| title: '基本信息', | |||
| align: 'center', | |||
| children: [ | |||
| { | |||
| title: '实例 ID', | |||
| @@ -120,7 +121,7 @@ function ExperimentComparison() { | |||
| width: 180, | |||
| fixed: 'left', | |||
| align: 'center', | |||
| render: tableCellRender(false, dateFormatter), | |||
| render: tableCellRender(false, TableCellValueType.Date), | |||
| }, | |||
| { | |||
| title: '运行状态', | |||
| @@ -128,7 +129,7 @@ function ExperimentComparison() { | |||
| key: 'status', | |||
| width: 100, | |||
| fixed: 'left', | |||
| align: 'center', | |||
| // align: 'center', | |||
| render: ExperimentStatusCell, | |||
| }, | |||
| { | |||
| @@ -138,7 +139,7 @@ function ExperimentComparison() { | |||
| width: 180, | |||
| fixed: 'left', | |||
| align: 'center', | |||
| render: tableCellRender(true, arrayFormatter()), | |||
| render: tableCellRender(true, TableCellValueType.Array), | |||
| ellipsis: { showTitle: false }, | |||
| }, | |||
| ], | |||
| @@ -1,4 +1,3 @@ | |||
| import CommonTableCell from '@/components/CommonTableCell'; | |||
| import KFIcon from '@/components/KFIcon'; | |||
| import { ExperimentStatus, TensorBoardStatus } from '@/enums'; | |||
| import { | |||
| @@ -15,6 +14,7 @@ import { | |||
| import { getWorkflow } from '@/services/pipeline/index.js'; | |||
| import themes from '@/styles/theme.less'; | |||
| import { to } from '@/utils/promise'; | |||
| import tableCellRender, { TableCellValueType } from '@/utils/table'; | |||
| import { modalConfirm } from '@/utils/ui'; | |||
| import { App, Button, ConfigProvider, Dropdown, Space, Table } from 'antd'; | |||
| import classNames from 'classnames'; | |||
| @@ -273,8 +273,7 @@ function Experiment() { | |||
| }; | |||
| // 跳转到流水线 | |||
| const gotoPipeline = (e, record) => { | |||
| e.stopPropagation(); | |||
| const gotoPipeline = (record) => { | |||
| navigate({ pathname: `/pipeline/template/info/${record.workflow_id}` }); | |||
| }; | |||
| @@ -348,25 +347,23 @@ function Experiment() { | |||
| title: '实验名称', | |||
| dataIndex: 'name', | |||
| key: 'name', | |||
| render: (text) => <div>{text}</div>, | |||
| render: tableCellRender(), | |||
| width: '16%', | |||
| }, | |||
| { | |||
| title: '关联流水线名称', | |||
| dataIndex: 'workflow_name', | |||
| key: 'workflow_name', | |||
| render: (text, record) => ( | |||
| <a className="kf-table-row-link" onClick={(e) => gotoPipeline(e, record)}> | |||
| {text} | |||
| </a> | |||
| ), | |||
| render: tableCellRender(false, TableCellValueType.Link, { | |||
| onClick: gotoPipeline, | |||
| }), | |||
| width: '16%', | |||
| }, | |||
| { | |||
| title: '实验描述', | |||
| dataIndex: 'description', | |||
| key: 'description', | |||
| render: CommonTableCell(true), | |||
| render: tableCellRender(true), | |||
| ellipsis: { showTitle: false }, | |||
| }, | |||
| { | |||
| @@ -395,7 +392,6 @@ function Experiment() { | |||
| ); | |||
| }, | |||
| }, | |||
| { | |||
| title: '操作', | |||
| key: 'action', | |||
| @@ -3,8 +3,6 @@ | |||
| * @Date: 2024-04-16 13:58:08 | |||
| * @Description: 镜像详情 | |||
| */ | |||
| import CommonTableCell from '@/components/CommonTableCell'; | |||
| import DateTableCell from '@/components/DateTableCell'; | |||
| import KFIcon from '@/components/KFIcon'; | |||
| import PageTitle from '@/components/PageTitle'; | |||
| import SubAreaTitle from '@/components/SubAreaTitle'; | |||
| @@ -20,6 +18,7 @@ import themes from '@/styles/theme.less'; | |||
| import { formatDate } from '@/utils/date'; | |||
| import { to } from '@/utils/promise'; | |||
| import SessionStorage from '@/utils/sessionStorage'; | |||
| import tableCellRender, { TableCellValueType } from '@/utils/table'; | |||
| import { modalConfirm } from '@/utils/ui'; | |||
| import { useNavigate, useParams } from '@umijs/max'; | |||
| import { | |||
| @@ -156,13 +155,13 @@ function MirrorInfo() { | |||
| dataIndex: 'tag_name', | |||
| key: 'tag_name', | |||
| width: '25%', | |||
| render: CommonTableCell(), | |||
| render: tableCellRender(), | |||
| }, | |||
| { | |||
| title: '镜像地址', | |||
| dataIndex: 'url', | |||
| key: 'url', | |||
| render: CommonTableCell(), | |||
| render: tableCellRender(), | |||
| }, | |||
| { | |||
| title: '状态', | |||
| @@ -176,14 +175,14 @@ function MirrorInfo() { | |||
| dataIndex: 'file_size', | |||
| key: 'file_size', | |||
| width: 150, | |||
| render: CommonTableCell(), | |||
| render: tableCellRender(), | |||
| }, | |||
| { | |||
| title: '创建时间', | |||
| dataIndex: 'create_time', | |||
| key: 'create_time', | |||
| width: 200, | |||
| render: DateTableCell, | |||
| render: tableCellRender(false, TableCellValueType.Date), | |||
| }, | |||
| { | |||
| title: '操作', | |||
| @@ -3,8 +3,6 @@ | |||
| * @Date: 2024-04-16 13:58:08 | |||
| * @Description: 镜像列表 | |||
| */ | |||
| import CommonTableCell from '@/components/CommonTableCell'; | |||
| import DateTableCell from '@/components/DateTableCell'; | |||
| import KFIcon from '@/components/KFIcon'; | |||
| import { CommonTabKeys } from '@/enums'; | |||
| import { useCacheState } from '@/hooks/pageCacheState'; | |||
| @@ -12,6 +10,7 @@ import { deleteMirrorReq, getMirrorListReq } from '@/services/mirror'; | |||
| import themes from '@/styles/theme.less'; | |||
| import { to } from '@/utils/promise'; | |||
| import SessionStorage from '@/utils/sessionStorage'; | |||
| import tableCellRender, { TableCellValueType } from '@/utils/table'; | |||
| import { modalConfirm } from '@/utils/ui'; | |||
| import { useNavigate } from '@umijs/max'; | |||
| import { | |||
| @@ -169,21 +168,21 @@ function MirrorList() { | |||
| dataIndex: 'name', | |||
| key: 'name', | |||
| width: '30%', | |||
| render: CommonTableCell(), | |||
| render: tableCellRender(), | |||
| }, | |||
| { | |||
| title: '版本数据', | |||
| dataIndex: 'version_count', | |||
| key: 'version_count', | |||
| width: '15%', | |||
| render: CommonTableCell(), | |||
| render: tableCellRender(), | |||
| }, | |||
| { | |||
| title: '镜像描述', | |||
| dataIndex: 'description', | |||
| key: 'description', | |||
| width: '35%', | |||
| render: CommonTableCell(true), | |||
| render: tableCellRender(true), | |||
| ellipsis: { showTitle: false }, | |||
| }, | |||
| { | |||
| @@ -191,7 +190,7 @@ function MirrorList() { | |||
| dataIndex: 'create_time', | |||
| key: 'create_time', | |||
| width: '20%', | |||
| render: DateTableCell, | |||
| render: tableCellRender(false, TableCellValueType.Date), | |||
| }, | |||
| { | |||
| title: '操作', | |||
| @@ -3,8 +3,6 @@ | |||
| * @Date: 2024-04-16 13:58:08 | |||
| * @Description: 模型部署服务列表 | |||
| */ | |||
| import CommonTableCell from '@/components/CommonTableCell'; | |||
| import DateTableCell from '@/components/DateTableCell'; | |||
| import KFIcon from '@/components/KFIcon'; | |||
| import PageTitle from '@/components/PageTitle'; | |||
| import { serviceTypeOptions } from '@/enums'; | |||
| @@ -13,6 +11,7 @@ import { deleteServiceReq, getServiceListReq } from '@/services/modelDeployment' | |||
| import themes from '@/styles/theme.less'; | |||
| import { to } from '@/utils/promise'; | |||
| import SessionStorage from '@/utils/sessionStorage'; | |||
| import tableCellRender, { TableCellValueType } from '@/utils/table'; | |||
| import { modalConfirm } from '@/utils/ui'; | |||
| import { useNavigate } from '@umijs/max'; | |||
| import { | |||
| @@ -190,42 +189,39 @@ function ModelDeployment() { | |||
| dataIndex: 'index', | |||
| key: 'index', | |||
| width: '20%', | |||
| render(_text, _record, index) { | |||
| return <span>{(pagination.current! - 1) * pagination.pageSize! + index + 1}</span>; | |||
| }, | |||
| render: tableCellRender(false, TableCellValueType.PageIndex, { | |||
| page: pagination.current! - 1, | |||
| pageSize: pagination.pageSize!, | |||
| }), | |||
| }, | |||
| { | |||
| title: '服务名称', | |||
| dataIndex: 'service_name', | |||
| key: 'service_name', | |||
| width: '20%', | |||
| render: (text, record) => { | |||
| return ( | |||
| <a className="kf-table-row-link" onClick={() => toDetail(record)}> | |||
| {text} | |||
| </a> | |||
| ); | |||
| }, | |||
| render: tableCellRender(false, TableCellValueType.Link, { | |||
| onClick: toDetail, | |||
| }), | |||
| }, | |||
| { | |||
| title: '服务类型', | |||
| dataIndex: 'service_type_name', | |||
| key: 'service_type_name', | |||
| width: '20%', | |||
| render: CommonTableCell(), | |||
| render: tableCellRender(), | |||
| }, | |||
| { | |||
| title: '版本数量', | |||
| dataIndex: 'version_count', | |||
| key: 'version_count', | |||
| width: '20%', | |||
| render: CommonTableCell(), | |||
| render: tableCellRender(), | |||
| }, | |||
| { | |||
| title: '服务描述', | |||
| dataIndex: 'description', | |||
| key: 'description', | |||
| render: CommonTableCell(), | |||
| render: tableCellRender(), | |||
| width: '20%', | |||
| }, | |||
| { | |||
| @@ -233,7 +229,7 @@ function ModelDeployment() { | |||
| dataIndex: 'update_time', | |||
| key: 'update_time', | |||
| width: '20%', | |||
| render: DateTableCell, | |||
| render: tableCellRender(false, TableCellValueType.Date), | |||
| }, | |||
| { | |||
| title: '操作', | |||
| @@ -4,7 +4,6 @@ | |||
| * @Description: 模型部署列表 | |||
| */ | |||
| import BasicInfo from '@/components/BasicInfo'; | |||
| import CommonTableCell from '@/components/CommonTableCell'; | |||
| import KFIcon from '@/components/KFIcon'; | |||
| import PageTitle from '@/components/PageTitle'; | |||
| import SubAreaTitle from '@/components/SubAreaTitle'; | |||
| @@ -21,6 +20,7 @@ import themes from '@/styles/theme.less'; | |||
| import { formatDate } from '@/utils/date'; | |||
| import { to } from '@/utils/promise'; | |||
| import SessionStorage from '@/utils/sessionStorage'; | |||
| import tableCellRender, { TableCellValueType } from '@/utils/table'; | |||
| import { modalConfirm } from '@/utils/ui'; | |||
| import { useNavigate, useParams } from '@umijs/max'; | |||
| import { | |||
| @@ -222,31 +222,24 @@ function ServiceInfo() { | |||
| dataIndex: 'index', | |||
| key: 'index', | |||
| width: '20%', | |||
| render(_text, _record, index) { | |||
| return <span>{(pagination.current! - 1) * pagination.pageSize! + index + 1}</span>; | |||
| }, | |||
| render: tableCellRender(false, TableCellValueType.PageIndex, { | |||
| page: pagination.current! - 1, | |||
| pageSize: pagination.pageSize!, | |||
| }), | |||
| }, | |||
| { | |||
| title: '服务版本', | |||
| dataIndex: 'version', | |||
| key: 'version', | |||
| width: '20%', | |||
| render: CommonTableCell(), | |||
| render: tableCellRender(), | |||
| }, | |||
| { | |||
| title: '模型版本', | |||
| dataIndex: 'model', | |||
| dataIndex: ['model', 'show_value'], | |||
| key: 'model', | |||
| width: '20%', | |||
| render: (_text: string, record: ServiceVersionData) => ( | |||
| <Tooltip | |||
| title={record.model.show_value} | |||
| placement="topLeft" | |||
| overlayStyle={{ maxWidth: '400px' }} | |||
| > | |||
| <span>{record.model.show_value}</span> | |||
| </Tooltip> | |||
| ), | |||
| render: tableCellRender(true), | |||
| ellipsis: { showTitle: false }, | |||
| }, | |||
| { | |||
| @@ -261,14 +254,14 @@ function ServiceInfo() { | |||
| dataIndex: 'image', | |||
| key: 'image', | |||
| width: '20%', | |||
| render: CommonTableCell(true), | |||
| render: tableCellRender(true), | |||
| ellipsis: { showTitle: false }, | |||
| }, | |||
| { | |||
| title: '副本数量', | |||
| dataIndex: 'replicas', | |||
| key: 'replicas', | |||
| render: CommonTableCell(), | |||
| render: tableCellRender(), | |||
| width: '20%', | |||
| }, | |||
| { | |||
| @@ -1,5 +1,3 @@ | |||
| import CommonTableCell from '@/components/CommonTableCell'; | |||
| import DateTableCell from '@/components/DateTableCell'; | |||
| import KFIcon from '@/components/KFIcon'; | |||
| import KFModal from '@/components/KFModal'; | |||
| import { | |||
| @@ -11,6 +9,7 @@ import { | |||
| removeWorkflow, | |||
| } from '@/services/pipeline/index.js'; | |||
| import themes from '@/styles/theme.less'; | |||
| import tableCellRender, { TableCellValueType } from '@/utils/table'; | |||
| import { modalConfirm } from '@/utils/ui'; | |||
| import { App, Button, ConfigProvider, Form, Input, Space, Table } from 'antd'; | |||
| import classNames from 'classnames'; | |||
| @@ -41,8 +40,7 @@ const Pipeline = () => { | |||
| } | |||
| }); | |||
| }; | |||
| const routeToEdit = (e, record) => { | |||
| e.stopPropagation(); | |||
| const routeToEdit = (record) => { | |||
| navigate({ pathname: `/pipeline/template/info/${record.id}` }); | |||
| }; | |||
| const showModal = () => { | |||
| @@ -114,38 +112,37 @@ const Pipeline = () => { | |||
| key: 'index', | |||
| width: 120, | |||
| align: 'center', | |||
| render(text, record, index) { | |||
| return <span>{(pageOption.current.page - 1) * pageOption.current.size + index + 1}</span>; | |||
| }, | |||
| render: tableCellRender(false, TableCellValueType.PageIndex, { | |||
| page: pageOption.current.page - 1, | |||
| size: pageOption.current.size, | |||
| }), | |||
| }, | |||
| { | |||
| title: '流水线名称', | |||
| dataIndex: 'name', | |||
| key: 'name', | |||
| render: (text, record) => ( | |||
| <a className="kf-table-row-link" onClick={(e) => routeToEdit(e, record)}> | |||
| {text} | |||
| </a> | |||
| ), | |||
| render: tableCellRender(false, TableCellValueType.Link, { | |||
| onClick: routeToEdit, | |||
| }), | |||
| }, | |||
| { | |||
| title: '流水线描述', | |||
| dataIndex: 'description', | |||
| key: 'description', | |||
| render: CommonTableCell(true), | |||
| render: tableCellRender(true), | |||
| ellipsis: { showTitle: false }, | |||
| }, | |||
| { | |||
| title: '创建时间', | |||
| dataIndex: 'create_time', | |||
| key: 'create_time', | |||
| render: DateTableCell, | |||
| render: tableCellRender(false, TableCellValueType.Date), | |||
| }, | |||
| { | |||
| title: '修改时间', | |||
| dataIndex: 'update_time', | |||
| key: 'update_time', | |||
| render: DateTableCell, | |||
| render: tableCellRender(false, TableCellValueType.Date), | |||
| }, | |||
| { | |||
| title: '操作', | |||
| @@ -1,22 +1,33 @@ | |||
| /* | |||
| * @Author: 赵伟 | |||
| * @Date: 2024-06-26 10:05:52 | |||
| * @Description: 列表自定义 render | |||
| * @Description: Table cell 自定义 render | |||
| */ | |||
| import { formatDate } from '@/utils/date'; | |||
| import { Tooltip } from 'antd'; | |||
| import dayjs from 'dayjs'; | |||
| type TableCellFormatter = (value?: any | null) => string | undefined | null; | |||
| export enum TableCellValueType { | |||
| Index = 'Index', | |||
| PageIndex = 'PageIndex', | |||
| Text = 'Text', | |||
| Date = 'Date', | |||
| Array = 'Array', | |||
| Link = 'Link', | |||
| } | |||
| // 字符串转换函数 | |||
| export const stringFormatter: TableCellFormatter = (value?: any | null) => { | |||
| return value; | |||
| export type TableCellValueOptions<T> = { | |||
| page?: number; | |||
| pageSize?: number; | |||
| property?: string; | |||
| onClick?: (record: T, e: React.MouseEvent) => void; | |||
| }; | |||
| type TableCellFormatter = (value: any | undefined | null) => string | undefined | null; | |||
| // 日期转换函数 | |||
| export const dateFormatter: TableCellFormatter = (value?: any | null) => { | |||
| const formatDateText: TableCellFormatter = (value?: any | null) => { | |||
| if (value === undefined || value === null || value === '') { | |||
| return null; | |||
| } | |||
| @@ -26,8 +37,12 @@ export const dateFormatter: TableCellFormatter = (value?: any | null) => { | |||
| return formatDate(value); | |||
| }; | |||
| // 数组转换函数 | |||
| export function arrayFormatter(property?: string) { | |||
| /** | |||
| * 数组转换函数,将数组元素转换为字符串,用逗号分隔 | |||
| * @param {string} property 如果数组元素是对象,那么取数组元素的某个属性 | |||
| * @returns {TableCellFormatter} Table cell 渲染函数 | |||
| */ | |||
| function formatArray(property?: string): TableCellFormatter { | |||
| return (value?: any | null): ReturnType<TableCellFormatter> => { | |||
| if ( | |||
| value === undefined || | |||
| @@ -38,31 +53,75 @@ export function arrayFormatter(property?: string) { | |||
| return null; | |||
| } | |||
| let list = value; | |||
| if (property && typeof value[0] === 'object') { | |||
| list = value.map((item) => item[property]); | |||
| } | |||
| const list = | |||
| property && typeof value[0] === 'object' ? value.map((item) => item[property]) : value; | |||
| return list.join(','); | |||
| }; | |||
| } | |||
| function tableCellRender(ellipsis: boolean = false, format: TableCellFormatter = stringFormatter) { | |||
| return (value?: any | null) => { | |||
| const text = format(value); | |||
| function tableCellRender<T>( | |||
| ellipsis: boolean = false, | |||
| type: TableCellValueType = TableCellValueType.Text, | |||
| options?: TableCellValueOptions<T>, | |||
| ) { | |||
| return (value: any | undefined | null, record: T, index: number) => { | |||
| let text = value; | |||
| switch (type) { | |||
| case TableCellValueType.Index: | |||
| text = index + 1; | |||
| break; | |||
| case TableCellValueType.PageIndex: | |||
| text = (options?.page ?? 1) * (options?.pageSize ?? 10) + index + 1; | |||
| break; | |||
| case TableCellValueType.Text: | |||
| case TableCellValueType.Link: | |||
| text = value; | |||
| break; | |||
| case TableCellValueType.Date: | |||
| text = formatDateText(value); | |||
| break; | |||
| case TableCellValueType.Array: | |||
| text = formatArray(options?.property)(value); | |||
| break; | |||
| default: | |||
| break; | |||
| } | |||
| if (ellipsis && text) { | |||
| return ( | |||
| <Tooltip title={text} placement="topLeft" overlayStyle={{ maxWidth: '400px' }}> | |||
| {renderCell(text)} | |||
| {renderCell(text, type === TableCellValueType.Link, record, options?.onClick)} | |||
| </Tooltip> | |||
| ); | |||
| } else { | |||
| return renderCell(text); | |||
| return renderCell(text, type === TableCellValueType.Link, record, options?.onClick); | |||
| } | |||
| }; | |||
| } | |||
| function renderCell(text?: any | null) { | |||
| function renderCell<T>( | |||
| text: any | undefined | null, | |||
| isLink: boolean, | |||
| record: T, | |||
| onClick?: (record: T, e: React.MouseEvent) => void, | |||
| ) { | |||
| return isLink ? renderLink(text, record, onClick) : renderText(text); | |||
| } | |||
| function renderText(text: any | undefined | null) { | |||
| return <span>{text ?? '--'}</span>; | |||
| } | |||
| function renderLink<T>( | |||
| text: any | undefined | null, | |||
| record: T, | |||
| onClick?: (record: T, e: React.MouseEvent) => void, | |||
| ) { | |||
| return ( | |||
| <a className="kf-table-row-link" onClick={(e) => onClick?.(record, e)}> | |||
| {text} | |||
| </a> | |||
| ); | |||
| } | |||
| export default tableCellRender; | |||