refactor: converge semi metric rail
This commit is contained in:
@@ -346,6 +346,10 @@ describe('V2 production entry', () => {
|
|||||||
expect(corePageSources.OperationsPage).toContain('<Card className="v2-ops-overview"');
|
expect(corePageSources.OperationsPage).toContain('<Card className="v2-ops-overview"');
|
||||||
expect(corePageSources.OperationsPage).toContain("from '../shared/WorkspaceMetricRail'");
|
expect(corePageSources.OperationsPage).toContain("from '../shared/WorkspaceMetricRail'");
|
||||||
expect(corePageSources.OperationsPage).toContain('<WorkspaceMetricRail');
|
expect(corePageSources.OperationsPage).toContain('<WorkspaceMetricRail');
|
||||||
|
expect(workspaceMetricRailSource).toContain("variant: 'queue'");
|
||||||
|
expect(workspaceMetricRailSource).not.toContain('CardGroup');
|
||||||
|
expect(workspaceMetricRailSource).not.toContain('primaryValueClassName');
|
||||||
|
expect(workspaceMetricRailSource).not.toContain('secondaryClassName');
|
||||||
expect(corePageSources.OperationsPage).not.toContain('<OpsMetric');
|
expect(corePageSources.OperationsPage).not.toContain('<OpsMetric');
|
||||||
expect(corePageSources.OperationsPage).toContain('<Card className="v2-ops-panel v2-ops-links"');
|
expect(corePageSources.OperationsPage).toContain('<Card className="v2-ops-panel v2-ops-links"');
|
||||||
expect(corePageSources.OperationsPage).toContain('<article className={`v2-ops-link-card');
|
expect(corePageSources.OperationsPage).toContain('<article className={`v2-ops-link-card');
|
||||||
@@ -484,9 +488,9 @@ describe('V2 production entry', () => {
|
|||||||
expect(corePageSources.StatisticsPage).toContain('<PanelEmpty className="v2-mileage-empty"');
|
expect(corePageSources.StatisticsPage).toContain('<PanelEmpty className="v2-mileage-empty"');
|
||||||
expect(corePageSources.StatisticsPage).not.toContain('<table className="v2-mileage-table"');
|
expect(corePageSources.StatisticsPage).not.toContain('<table className="v2-mileage-table"');
|
||||||
expect(corePageSources.StatisticsPage).not.toContain('<input');
|
expect(corePageSources.StatisticsPage).not.toContain('<input');
|
||||||
expect(workspaceMetricRailSource).toContain("import { Button, Card, CardGroup } from '@douyinfe/semi-ui'");
|
expect(workspaceMetricRailSource).toContain("import { Button, Card } from '@douyinfe/semi-ui'");
|
||||||
expect(workspaceMetricRailSource).toContain('<Card className={className}');
|
expect(workspaceMetricRailSource).not.toContain('CardGroup');
|
||||||
expect(workspaceMetricRailSource).toContain('<CardGroup className={secondaryClassName}');
|
expect(workspaceMetricRailSource).not.toContain('secondaryClassName');
|
||||||
expect(workspaceMetricRailSource).toContain("variant: 'queue'");
|
expect(workspaceMetricRailSource).toContain("variant: 'queue'");
|
||||||
expect(workspaceMetricRailSource).toContain('className={`v2-workspace-metric-rail is-queue');
|
expect(workspaceMetricRailSource).toContain('className={`v2-workspace-metric-rail is-queue');
|
||||||
expect(workspaceMetricRailSource).toContain('className="v2-workspace-metric-action"');
|
expect(workspaceMetricRailSource).toContain('className="v2-workspace-metric-action"');
|
||||||
|
|||||||
@@ -3,28 +3,7 @@ import { describe, expect, it, vi } from 'vitest';
|
|||||||
import { WorkspaceMetricRail } from './WorkspaceMetricRail';
|
import { WorkspaceMetricRail } from './WorkspaceMetricRail';
|
||||||
|
|
||||||
describe('WorkspaceMetricRail', () => {
|
describe('WorkspaceMetricRail', () => {
|
||||||
it('renders one primary outcome and supporting facts as accessible Semi cards', () => {
|
it('renders one accessible, list-first Semi metric rail', () => {
|
||||||
const view = render(<WorkspaceMetricRail
|
|
||||||
ariaLabel="查询统计"
|
|
||||||
className="test-rail"
|
|
||||||
cardClassName="test-card"
|
|
||||||
secondaryClassName="test-secondary"
|
|
||||||
primaryValueClassName="test-primary-value"
|
|
||||||
primary={{ label: '结果行数', value: '1,024', note: '来自 20 辆车辆' }}
|
|
||||||
secondary={[
|
|
||||||
{ label: '车辆数', value: '20', note: '当前授权范围', className: 'is-vehicles' },
|
|
||||||
{ label: '数据来源', value: 'GB32960', note: '全部协议来源', className: 'is-sources' }
|
|
||||||
]}
|
|
||||||
/>);
|
|
||||||
|
|
||||||
expect(view.container.querySelector('.test-rail.semi-card')).toHaveAttribute('aria-label', '查询统计');
|
|
||||||
expect(view.container.querySelector('.test-card.is-primary .test-primary-value')).toHaveTextContent('1,024');
|
|
||||||
expect(view.container.querySelector('.test-secondary.semi-card-group')).toBeInTheDocument();
|
|
||||||
expect(view.container.querySelectorAll('.test-card.semi-card')).toHaveLength(3);
|
|
||||||
expect(screen.getByLabelText('车辆数:20;当前授权范围')).toHaveClass('is-vehicles');
|
|
||||||
});
|
|
||||||
|
|
||||||
it('renders a list-first queue variant inside one Semi card', () => {
|
|
||||||
const view = render(<WorkspaceMetricRail
|
const view = render(<WorkspaceMetricRail
|
||||||
variant="queue"
|
variant="queue"
|
||||||
ariaLabel="处置队列概览"
|
ariaLabel="处置队列概览"
|
||||||
|
|||||||
@@ -1,13 +1,6 @@
|
|||||||
import { Button, Card, CardGroup } from '@douyinfe/semi-ui';
|
import { Button, Card } from '@douyinfe/semi-ui';
|
||||||
import type { ReactNode } from 'react';
|
import type { ReactNode } from 'react';
|
||||||
|
|
||||||
export type WorkspaceMetricRailItem = {
|
|
||||||
label: string;
|
|
||||||
value: ReactNode;
|
|
||||||
note: string;
|
|
||||||
className?: string;
|
|
||||||
};
|
|
||||||
|
|
||||||
export type WorkspaceQueueMetricRailItem = {
|
export type WorkspaceQueueMetricRailItem = {
|
||||||
label: string;
|
label: string;
|
||||||
value: ReactNode;
|
value: ReactNode;
|
||||||
@@ -19,16 +12,6 @@ export type WorkspaceQueueMetricRailItem = {
|
|||||||
onClick?: () => void;
|
onClick?: () => void;
|
||||||
};
|
};
|
||||||
|
|
||||||
type WorkspaceSummaryMetricRailProps = {
|
|
||||||
ariaLabel: string;
|
|
||||||
primary: WorkspaceMetricRailItem;
|
|
||||||
secondary: WorkspaceMetricRailItem[];
|
|
||||||
className: string;
|
|
||||||
cardClassName: string;
|
|
||||||
secondaryClassName: string;
|
|
||||||
primaryValueClassName?: string;
|
|
||||||
};
|
|
||||||
|
|
||||||
type WorkspaceQueueMetricRailProps = {
|
type WorkspaceQueueMetricRailProps = {
|
||||||
variant: 'queue';
|
variant: 'queue';
|
||||||
ariaLabel: string;
|
ariaLabel: string;
|
||||||
@@ -37,8 +20,7 @@ type WorkspaceQueueMetricRailProps = {
|
|||||||
context?: ReactNode;
|
context?: ReactNode;
|
||||||
};
|
};
|
||||||
|
|
||||||
export function WorkspaceMetricRail(props: WorkspaceSummaryMetricRailProps | WorkspaceQueueMetricRailProps) {
|
export function WorkspaceMetricRail(props: WorkspaceQueueMetricRailProps) {
|
||||||
if ('items' in props) {
|
|
||||||
const hasContext = props.context != null;
|
const hasContext = props.context != null;
|
||||||
return <Card className={`v2-workspace-metric-rail is-queue${hasContext ? ' has-context' : ''} ${props.className}`} bodyStyle={{ padding: 0 }}>
|
return <Card className={`v2-workspace-metric-rail is-queue${hasContext ? ' has-context' : ''} ${props.className}`} bodyStyle={{ padding: 0 }}>
|
||||||
<div className="v2-workspace-metric-list" role="list" aria-label={props.ariaLabel}>
|
<div className="v2-workspace-metric-list" role="list" aria-label={props.ariaLabel}>
|
||||||
@@ -75,35 +57,4 @@ export function WorkspaceMetricRail(props: WorkspaceSummaryMetricRailProps | Wor
|
|||||||
</div>
|
</div>
|
||||||
{hasContext ? <div className="v2-workspace-metric-context">{props.context}</div> : null}
|
{hasContext ? <div className="v2-workspace-metric-context">{props.context}</div> : null}
|
||||||
</Card>;
|
</Card>;
|
||||||
}
|
|
||||||
|
|
||||||
const {
|
|
||||||
ariaLabel,
|
|
||||||
primary,
|
|
||||||
secondary,
|
|
||||||
className,
|
|
||||||
cardClassName,
|
|
||||||
secondaryClassName,
|
|
||||||
primaryValueClassName
|
|
||||||
} = props;
|
|
||||||
const cardClass = (item: WorkspaceMetricRailItem, primaryCard = false) => [
|
|
||||||
cardClassName,
|
|
||||||
primaryCard ? 'is-primary' : '',
|
|
||||||
item.className ?? ''
|
|
||||||
].filter(Boolean).join(' ');
|
|
||||||
|
|
||||||
return <Card className={className} aria-label={ariaLabel} bodyStyle={{ padding: 0 }}>
|
|
||||||
<Card className={cardClass(primary, true)} bodyStyle={{ padding: 0 }} aria-label={`${primary.label}:${primary.value};${primary.note}`}>
|
|
||||||
<small>{primary.label}</small>
|
|
||||||
<strong className={primaryValueClassName}>{primary.value}</strong>
|
|
||||||
<span title={primary.note}>{primary.note}</span>
|
|
||||||
</Card>
|
|
||||||
<CardGroup className={secondaryClassName} type="grid" spacing={0}>
|
|
||||||
{secondary.map((item) => <Card className={cardClass(item)} bodyStyle={{ padding: 0 }} aria-label={`${item.label}:${item.value};${item.note}`} key={item.label}>
|
|
||||||
<small>{item.label}</small>
|
|
||||||
<strong>{item.value}</strong>
|
|
||||||
<span title={item.note}>{item.note}</span>
|
|
||||||
</Card>)}
|
|
||||||
</CardGroup>
|
|
||||||
</Card>;
|
|
||||||
}
|
}
|
||||||
|
|||||||
Reference in New Issue
Block a user