mirror of
https://github.com/portainer/portainer.git
synced 2025-08-04 21:35:23 +02:00
feat(kube): add a11y props for smoke tests [EE-6747] (#11262)
This commit is contained in:
parent
d44f57ed6f
commit
b4f4c3212a
26 changed files with 143 additions and 62 deletions
|
@ -43,6 +43,7 @@ export function PageHeader({
|
|||
onClick={onClickedRefresh}
|
||||
className="m-0 p-0 focus:text-inherit"
|
||||
disabled={loading}
|
||||
title="Refresh page"
|
||||
>
|
||||
<RefreshCw className="icon" />
|
||||
</Button>
|
||||
|
|
|
@ -29,6 +29,7 @@ export function TextTip({
|
|||
'small gap-1 align-top text-xs',
|
||||
inline ? 'inline-flex' : 'flex'
|
||||
)}
|
||||
role="status"
|
||||
>
|
||||
<Icon icon={icon} mode={getMode(color)} className="!mt-0.5 flex-none" />
|
||||
|
||||
|
|
|
@ -169,7 +169,7 @@ export function Datatable<D extends DefaultType>({
|
|||
const selectedItems = selectedRowModel.rows.map((row) => row.original);
|
||||
|
||||
return (
|
||||
<Table.Container noWidget={noWidget}>
|
||||
<Table.Container noWidget={noWidget} aria-label={title}>
|
||||
<DatatableHeader
|
||||
onSearchChange={handleSearchBarChange}
|
||||
searchValue={settings.search}
|
||||
|
|
|
@ -5,24 +5,30 @@ import { Widget, WidgetBody } from '@@/Widget';
|
|||
interface Props {
|
||||
// workaround to remove the widget, ideally we should have a different component to wrap the table with a widget
|
||||
noWidget?: boolean;
|
||||
'aria-label'?: string;
|
||||
}
|
||||
|
||||
export function TableContainer({
|
||||
children,
|
||||
noWidget = false,
|
||||
'aria-label': ariaLabel,
|
||||
}: PropsWithChildren<Props>) {
|
||||
if (noWidget) {
|
||||
return <div className="datatable">{children}</div>;
|
||||
return (
|
||||
<section className="datatable" aria-label={ariaLabel}>
|
||||
{children}
|
||||
</section>
|
||||
);
|
||||
}
|
||||
|
||||
return (
|
||||
<div className="row">
|
||||
<div className="col-sm-12">
|
||||
<div className="datatable">
|
||||
<section className="datatable" aria-label={ariaLabel}>
|
||||
<Widget>
|
||||
<WidgetBody className="no-padding">{children}</WidgetBody>
|
||||
</Widget>
|
||||
</div>
|
||||
</section>
|
||||
</div>
|
||||
</div>
|
||||
);
|
||||
|
|
|
@ -17,6 +17,7 @@ export interface Props {
|
|||
dataCy?: string;
|
||||
// true if you want to always show the tooltip
|
||||
visibleTooltip?: boolean;
|
||||
disabled?: boolean;
|
||||
}
|
||||
|
||||
export function Slider({
|
||||
|
@ -27,6 +28,7 @@ export function Slider({
|
|||
onChange,
|
||||
dataCy,
|
||||
visibleTooltip: visible,
|
||||
disabled,
|
||||
}: Props) {
|
||||
const marks = {
|
||||
[min]: visible && value / max < 0.1 ? '' : translateMinValue(min),
|
||||
|
@ -34,14 +36,14 @@ export function Slider({
|
|||
};
|
||||
|
||||
return (
|
||||
<div className={styles.root}>
|
||||
<div className={styles.root} data-cy={dataCy}>
|
||||
<RcSlider
|
||||
handleRender={visible ? sliderTooltip : undefined}
|
||||
min={min}
|
||||
max={max}
|
||||
marks={marks}
|
||||
step={step}
|
||||
data-cy={dataCy}
|
||||
disabled={disabled}
|
||||
value={value}
|
||||
onChange={onChange}
|
||||
/>
|
||||
|
|
|
@ -10,6 +10,7 @@ export function SliderWithInput({
|
|||
step = 1,
|
||||
dataCy,
|
||||
visibleTooltip = false,
|
||||
inputId,
|
||||
}: {
|
||||
value: number;
|
||||
onChange: (value: number) => void;
|
||||
|
@ -18,6 +19,7 @@ export function SliderWithInput({
|
|||
dataCy: string;
|
||||
step?: number;
|
||||
visibleTooltip?: boolean;
|
||||
inputId?: string;
|
||||
}) {
|
||||
return (
|
||||
<div className="flex items-center gap-6">
|
||||
|
@ -44,6 +46,7 @@ export function SliderWithInput({
|
|||
onChange={(e) => onChange(e.target.valueAsNumber)}
|
||||
className="w-32"
|
||||
data-cy={`${dataCy}Input`}
|
||||
id={inputId}
|
||||
/>
|
||||
</div>
|
||||
);
|
||||
|
|
|
@ -2,6 +2,7 @@ import clsx from 'clsx';
|
|||
|
||||
import { isLimitedToBE } from '@/react/portainer/feature-flags/feature-flags.service';
|
||||
import { FeatureId } from '@/react/portainer/feature-flags/enums';
|
||||
import { AutomationTestingProps } from '@/types';
|
||||
|
||||
import { BEFeatureIndicator } from '@@/BEFeatureIndicator';
|
||||
|
||||
|
@ -9,7 +10,7 @@ import './Switch.css';
|
|||
|
||||
import styles from './Switch.module.css';
|
||||
|
||||
export interface Props {
|
||||
export interface Props extends AutomationTestingProps {
|
||||
checked: boolean;
|
||||
id: string;
|
||||
name: string;
|
||||
|
@ -17,7 +18,6 @@ export interface Props {
|
|||
|
||||
index?: number;
|
||||
className?: string;
|
||||
dataCy?: string;
|
||||
disabled?: boolean;
|
||||
featureId?: FeatureId;
|
||||
}
|
||||
|
@ -27,7 +27,7 @@ export function Switch({
|
|||
checked,
|
||||
id,
|
||||
disabled,
|
||||
dataCy,
|
||||
'data-cy': dataCy,
|
||||
onChange,
|
||||
index,
|
||||
featureId,
|
||||
|
@ -42,6 +42,8 @@ export function Switch({
|
|||
business: limitedToBE,
|
||||
limited: limitedToBE,
|
||||
})}
|
||||
data-cy={dataCy}
|
||||
aria-checked={checked}
|
||||
>
|
||||
<input
|
||||
type="checkbox"
|
||||
|
@ -51,7 +53,7 @@ export function Switch({
|
|||
disabled={disabled || limitedToBE}
|
||||
onChange={({ target: { checked } }) => onChange(checked, index)}
|
||||
/>
|
||||
<span className="slider round before:content-['']" data-cy={dataCy} />
|
||||
<span className="slider round before:content-['']" />
|
||||
</label>
|
||||
{limitedToBE && <BEFeatureIndicator featureId={featureId} />}
|
||||
</>
|
||||
|
|
|
@ -3,13 +3,14 @@ import uuid from 'uuid';
|
|||
import { ComponentProps, PropsWithChildren, ReactNode } from 'react';
|
||||
|
||||
import { FeatureId } from '@/react/portainer/feature-flags/enums';
|
||||
import { AutomationTestingProps } from '@/types';
|
||||
|
||||
import { Tooltip } from '@@/Tip/Tooltip';
|
||||
|
||||
import styles from './SwitchField.module.css';
|
||||
import { Switch } from './Switch';
|
||||
|
||||
export interface Props {
|
||||
export interface Props extends AutomationTestingProps {
|
||||
label: string;
|
||||
checked: boolean;
|
||||
onChange(value: boolean, index?: number): void;
|
||||
|
@ -21,7 +22,7 @@ export interface Props {
|
|||
labelClass?: string;
|
||||
switchClass?: string;
|
||||
fieldClass?: string;
|
||||
dataCy?: string;
|
||||
|
||||
disabled?: boolean;
|
||||
featureId?: FeatureId;
|
||||
valueExplanation?: ReactNode;
|
||||
|
@ -35,7 +36,7 @@ export function SwitchField({
|
|||
name = uuid(),
|
||||
labelClass,
|
||||
fieldClass,
|
||||
dataCy,
|
||||
'data-cy': dataCy,
|
||||
disabled,
|
||||
onChange,
|
||||
featureId,
|
||||
|
@ -65,7 +66,7 @@ export function SwitchField({
|
|||
onChange={onChange}
|
||||
index={index}
|
||||
featureId={featureId}
|
||||
dataCy={dataCy}
|
||||
data-cy={dataCy}
|
||||
/>
|
||||
{valueExplanation && <span>{valueExplanation}</span>}
|
||||
</div>
|
||||
|
|
Loading…
Add table
Add a link
Reference in a new issue