| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
| |
|
|
| import React from 'react'; |
| import { |
| Card, |
| Button, |
| Spin, |
| Tabs, |
| TabPane, |
| Tag, |
| Empty, |
| } from '@douyinfe/semi-ui'; |
| import { Gauge, RefreshCw } from 'lucide-react'; |
| import { |
| IllustrationConstruction, |
| IllustrationConstructionDark, |
| } from '@douyinfe/semi-illustrations'; |
| import ScrollableContainer from '../common/ui/ScrollableContainer'; |
|
|
| const UptimePanel = ({ |
| uptimeData, |
| uptimeLoading, |
| activeUptimeTab, |
| setActiveUptimeTab, |
| loadUptimeData, |
| uptimeLegendData, |
| renderMonitorList, |
| CARD_PROPS, |
| ILLUSTRATION_SIZE, |
| t, |
| }) => { |
| return ( |
| <Card |
| {...CARD_PROPS} |
| className='shadow-sm !rounded-2xl lg:col-span-1' |
| title={ |
| <div className='flex items-center justify-between w-full gap-2'> |
| <div className='flex items-center gap-2'> |
| <Gauge size={16} /> |
| {t('服务可用性')} |
| </div> |
| <Button |
| icon={<RefreshCw size={14} />} |
| onClick={loadUptimeData} |
| loading={uptimeLoading} |
| size='small' |
| theme='borderless' |
| type='tertiary' |
| className='text-gray-500 hover:text-blue-500 hover:bg-blue-50 !rounded-full' |
| /> |
| </div> |
| } |
| bodyStyle={{ padding: 0 }} |
| > |
| {/* 内容区域 */} |
| <div className='relative'> |
| <Spin spinning={uptimeLoading}> |
| {uptimeData.length > 0 ? ( |
| uptimeData.length === 1 ? ( |
| <ScrollableContainer maxHeight='24rem'> |
| {renderMonitorList(uptimeData[0].monitors)} |
| </ScrollableContainer> |
| ) : ( |
| <Tabs |
| type='card' |
| collapsible |
| activeKey={activeUptimeTab} |
| onChange={setActiveUptimeTab} |
| size='small' |
| > |
| {uptimeData.map((group, groupIdx) => ( |
| <TabPane |
| tab={ |
| <span className='flex items-center gap-2'> |
| <Gauge size={14} /> |
| {group.categoryName} |
| <Tag |
| color={ |
| activeUptimeTab === group.categoryName |
| ? 'red' |
| : 'grey' |
| } |
| size='small' |
| shape='circle' |
| > |
| {group.monitors ? group.monitors.length : 0} |
| </Tag> |
| </span> |
| } |
| itemKey={group.categoryName} |
| key={groupIdx} |
| > |
| <ScrollableContainer maxHeight='21.5rem'> |
| {renderMonitorList(group.monitors)} |
| </ScrollableContainer> |
| </TabPane> |
| ))} |
| </Tabs> |
| ) |
| ) : ( |
| <div className='flex justify-center items-center py-8'> |
| <Empty |
| image={<IllustrationConstruction style={ILLUSTRATION_SIZE} />} |
| darkModeImage={ |
| <IllustrationConstructionDark style={ILLUSTRATION_SIZE} /> |
| } |
| title={t('暂无监控数据')} |
| description={t('请联系管理员在系统设置中配置Uptime')} |
| /> |
| </div> |
| )} |
| </Spin> |
| </div> |
| |
| {/* 图例 */} |
| {uptimeData.length > 0 && ( |
| <div className='p-3 bg-gray-50 rounded-b-2xl'> |
| <div className='flex flex-wrap gap-3 text-xs justify-center'> |
| {uptimeLegendData.map((legend, index) => ( |
| <div key={index} className='flex items-center gap-1'> |
| <div |
| className='w-2 h-2 rounded-full' |
| style={{ backgroundColor: legend.color }} |
| /> |
| <span className='text-gray-600'>{legend.label}</span> |
| </div> |
| ))} |
| </div> |
| </div> |
| )} |
| </Card> |
| ); |
| }; |
|
|
| export default UptimePanel; |
|
|