Skip to content
Merged
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
374 changes: 219 additions & 155 deletions package-lock.json

Large diffs are not rendered by default.

14 changes: 7 additions & 7 deletions package.json
Original file line number Diff line number Diff line change
Expand Up @@ -39,7 +39,7 @@
"dependencies": {
"@dnd-kit/helpers": "^0.3.2",
"@dnd-kit/react": "^0.5.0",
"@greenbone/ui-lib": "^2.8.1",
"@greenbone/ui-lib": "2.13.6-alpha0",
"@mantine/core": "^8.3.16",
"@mantine/dates": "^8.3.16",
"@mantine/notifications": "^8.3.16",
Expand All @@ -65,10 +65,10 @@
"lucide-react": "^1.23.0",
"memoize-one": "^6.0.0",
"prop-types": "^15.8.1",
"react": "^18.3.1",
"react-dom": "^18.3.1",
"react": "19.2.8",
"react-dom": "19.2.8",
"react-i18next": "^17.0.11",
"react-is": "^18.3.1",
"react-is": "19.2.8",
"react-redux": "^9.2.0",
"react-router": "^7.17.0",
"redux": "^5.0.1",
Expand All @@ -94,9 +94,9 @@
"@types/d3-scale": "^4.0.9",
"@types/d3-selection": "^3.0.11",
"@types/node": "^26.1.2",
"@types/react": "^18.3.18",
"@types/react-dom": "^18.3.5",
"@types/react-is": "^18.3.1",
"@types/react": "19.2.18",
"@types/react-dom": "19.2.4",
"@types/react-is": "19.2.0",
"@typescript-eslint/eslint-plugin": "^8.65.0",
"@typescript-eslint/parser": "^8.65.0",
"@vitejs/plugin-legacy": "^8.1.0",
Expand Down
6 changes: 4 additions & 2 deletions src/web/components/chart/Donut.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -48,7 +48,7 @@ interface DonutChartProps<TData extends DonutChartData> {
height: number;
data?: TData[];
innerRadius?: number;
svgRef?: React.RefObject<SVGSVGElement>;
svgRef?: React.RefObject<SVGSVGElement | null>;
show3d?: boolean;
showLegend?: boolean;
onDataClick?: (data: TData) => void;
Expand Down Expand Up @@ -285,7 +285,9 @@ class DonutChart<
return (
<StyledLayout align={['start', 'start']}>
<Svg
ref={setRef(svgRef as Ref<SVGSVGElement>, ref => (this.svg = ref))}
ref={setRef(svgRef as Ref<SVGSVGElement>, ref => {
this.svg = ref;
})}
height={height}
width={width}
>
Expand Down
4 changes: 3 additions & 1 deletion src/web/components/chart/HostsTopologyChart.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -528,7 +528,9 @@ class HostsTopologyChart extends React.Component<
</Layout>
)}
<Svg
ref={setRef(ref => (this.svg = ref), svgRef)}
ref={setRef(ref => {
this.svg = ref;
}, svgRef)}
$dragging={dragging}
height={height}
width={width}
Expand Down
2 changes: 1 addition & 1 deletion src/web/components/chart/base/Legend.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -39,7 +39,7 @@ interface LegendProps<TData extends LegendData = LegendData> {
onItemClick?: (d: TData) => void;
}

export type LegendRef = RefObject<HTMLElement>;
export type LegendRef = RefObject<HTMLElement | null>;

const StyledLegend = styled.div`
padding: 5px 10px;
Expand Down
2 changes: 1 addition & 1 deletion src/web/components/chart/base/Line.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -244,7 +244,7 @@ const LineChart = ({
y2Line,
onRangeSelected,
}: LineChartProps) => {
const legendRef: LegendRef = useRef(null);
const legendRef: LegendRef = useRef<HTMLElement | null>(null);
const svgElementRef = useRef<SVGSVGElement | null>(null);

const [displayInfo, setDisplayInfo] = useState(false);
Expand Down
4 changes: 2 additions & 2 deletions src/web/components/chart/base/Tooltip.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -71,8 +71,8 @@ const ToolTipDisplay = React.forwardRef(
);

class ToolTip extends React.Component<ToolTipProps, ToolTipState> {
target: React.RefObject<ToolTipTargetElement>;
tooltip: React.RefObject<HTMLElement>;
target: React.RefObject<ToolTipTargetElement | null>;
tooltip: React.RefObject<HTMLElement | null>;

constructor(props: ToolTipProps) {
super(props);
Expand Down
6 changes: 3 additions & 3 deletions src/web/components/chart/donut/Pie.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -13,16 +13,16 @@ import PropTypes from 'web/utils/prop-types';
const sortArcsByStartAngle = (a, b) => (a.startAngle > b.startAngle ? -1 : 1);

const Pie = ({
className,
className = undefined,
top = 0,
left = 0,
data,
innerRadiusX = 0,
outerRadiusX,
innerRadiusY,
outerRadiusY,
padAngle,
pieSort,
padAngle = undefined,
pieSort = undefined,
pieValue,
arcsSort = sortArcsByStartAngle,
children,
Expand Down
6 changes: 3 additions & 3 deletions src/web/components/dashboard/display/DataDisplay.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -53,7 +53,7 @@ interface DataDisplayRenderProps<TData, TState extends State> {
id: string;
width: number;
height: number;
svgRef: React.RefObject<SVGSVGElement>;
svgRef: React.RefObject<SVGSVGElement | null>;
data: TData[];
state: TState;
setState: SetStateFunc<TState>;
Expand Down Expand Up @@ -185,8 +185,8 @@ class DataDisplay<
TTransformedData,
TTransformProps = Record<string, unknown>,
> extends React.Component<TProps, DataDisplayState<TData, TTransformedData>> {
svgRef: React.RefObject<SVGSVGElement>;
downloadRef: React.RefObject<HTMLAnchorElement>;
svgRef: React.RefObject<SVGSVGElement | null>;
downloadRef: React.RefObject<HTMLAnchorElement | null>;
downloadSvgUrl?: string;
downloadCsvUrl?: string;

Expand Down
4 changes: 3 additions & 1 deletion src/web/components/form/Download.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -59,7 +59,9 @@ class Download extends React.Component<DownloadProps> {
const {filename} = this.props;
return (
<a
ref={ref => (this.anchor = ref)}
ref={ref => {
this.anchor = ref;
}}
aria-hidden
download={filename}
style={{display: 'none'}}
Expand Down
5 changes: 4 additions & 1 deletion src/web/components/form/ToggleButton.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -8,7 +8,10 @@ import styled from 'styled-components';
import {isDefined} from 'gmp/utils/identity';
import Theme from 'web/utils/theme';

interface StyledProps extends React.HTMLAttributes<HTMLDivElement> {
interface StyledProps extends Omit<
React.HTMLAttributes<HTMLDivElement>,
'onToggle'
> {
checked?: boolean;
disabled?: boolean;
width?: string;
Expand Down
11 changes: 6 additions & 5 deletions src/web/components/hover-card/ComponentWithHoverCard.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -3,13 +3,13 @@
* SPDX-License-Identifier: AGPL-3.0-or-later
*/

import {type ReactNode, type ReactElement, cloneElement} from 'react';
import {type ReactNode, cloneElement} from 'react';
import HoverCard from 'web/components/hover-card/HoverCard';
import useTranslation from 'web/hooks/useTranslation';

interface ComponentWithHoverCardProps {
/** The component (TextField, NumberField, etc.) */
slot: ReactElement;
slot: React.ReactElement<Record<string, unknown>>;
/** The help content to display in the hover card */
helpContent: ReactNode;
/** Aria label for the help button */
Expand Down Expand Up @@ -51,12 +51,13 @@ const ComponentWithHoverCard = ({
</HoverCard>
);

const slotProps = slot.props as Record<string, unknown>;
// Clone the slot element and add the HoverCard to its title
const slotWithHoverCard = cloneElement(slot, {
...slot.props,
title: slot.props.title ? (
...slotProps,
title: slotProps.title ? (
<>
{slot.props.title}
{slotProps.title}
{hoverCardElement}
Comment on lines +58 to 61
</>
) : (
Expand Down
10 changes: 6 additions & 4 deletions src/web/components/info-tip/ComponentWithInfoTip.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -9,7 +9,7 @@ import useTranslation from 'web/hooks/useTranslation';

interface ComponentWithInfoTipProps {
/** The component (TextField, NumberField, etc.) */
slot: ReactElement;
slot: ReactElement<Record<string, unknown>>;
/** The help content to display in the infotip */
helpContent: ReactNode;
/** Aria label for the help button */
Expand Down Expand Up @@ -55,12 +55,14 @@ const ComponentWithInfoTip = ({
</InfoTip>
);

const slotProps = slot.props;

// Clone the slot element and add the infoTip to its title
const slotWithInfoTip = cloneElement(slot, {
...slot.props,
title: slot.props.title ? (
...slotProps,
title: slotProps.title ? (
<>
{slot.props.title}
{slotProps.title}
{infoTipElement}
Comment on lines +63 to 66
</>
) : (
Expand Down
5 changes: 4 additions & 1 deletion src/web/components/tab/Tabs.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -24,7 +24,10 @@ const Tabs = (props: TabProps) => {
const children = React.Children.map(props.children, child => {
if (child && typeof child === 'object' && 'type' in child) {
if (child.type === TabPanels) {
return React.cloneElement(child, {activeTab});
return React.cloneElement(
child as React.ReactElement<{activeTab: number}>,
{activeTab},
);
} else if (child.type === TabList) {
return child;
}
Expand Down
5 changes: 4 additions & 1 deletion src/web/entities/__tests__/withEntitiesActions.test.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -24,7 +24,10 @@ describe('withEntitiesActions', () => {

render(<WrappedComponent entity={entity} someProp="test" />);

expect(MockComponent).toHaveBeenCalledWith({someProp: 'test', entity}, {});
expect(MockComponent).toHaveBeenCalledWith(
{someProp: 'test', entity},
undefined,
);
expect(screen.getByText('Mock Component')).toBeInTheDocument();
});

Expand Down
8 changes: 4 additions & 4 deletions src/web/entities/__tests__/withEntitiesFooter.test.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -47,7 +47,7 @@ describe('withEntitiesFooter tests', () => {
onTagsClick: mockProps.onTagsBulk,
onTrashClick: mockProps.onDeleteBulk,
}),
{},
undefined,
);
});

Expand Down Expand Up @@ -79,7 +79,7 @@ describe('withEntitiesFooter tests', () => {
onDeleteClick: mockProps.onDeleteBulk,
onTrashClick: mockProps.onDeleteBulk,
}),
{},
undefined,
);
});

Expand Down Expand Up @@ -112,7 +112,7 @@ describe('withEntitiesFooter tests', () => {
onDeleteClick: mockProps.onDeleteBulk,
onTrashClick: mockProps.onDeleteBulk,
}),
{},
undefined,
);
});

Expand All @@ -134,7 +134,7 @@ describe('withEntitiesFooter tests', () => {
onEnableUpdateToLatestClick: expect.any(Function),
onDisableUpdateToLatestClick: expect.any(Function),
}),
{},
undefined,
);
});
});
48 changes: 42 additions & 6 deletions src/web/entity/__tests__/Tags.test.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -73,7 +73,13 @@ describe('EntityTags tests', () => {
const gmp = createGmp();
const {render} = rendererWith({capabilities: true, gmp});

render(<EntityTags entity={entity} />);
render(
<EntityTags
entity={entity}
onChanged={testing.fn()}
onError={testing.fn()}
/>,
);

screen.getByTitle('User Tags (2)');
screen.getByText('Test Tag');
Expand All @@ -90,7 +96,13 @@ describe('EntityTags tests', () => {
const gmp = createGmp();
const {render} = rendererWith({capabilities: true, gmp});

render(<EntityTags entity={entity1} />);
render(
<EntityTags
entity={entity1}
onChanged={testing.fn()}
onError={testing.fn()}
/>,
);
screen.getByText('No user tags available');
});

Expand All @@ -102,7 +114,13 @@ describe('EntityTags tests', () => {
const gmp = createGmp();
const {render} = rendererWith({capabilities: true, gmp});

render(<EntityTags entity={entity2} />);
render(
<EntityTags
entity={entity2}
onChanged={testing.fn()}
onError={testing.fn()}
/>,
);
screen.getByText('No user tags available');
});

Expand All @@ -111,7 +129,13 @@ describe('EntityTags tests', () => {
const gmp = createGmp();
const {render} = rendererWith({capabilities: true, gmp});

render(<EntityTags entity={entity} />);
render(
<EntityTags
entity={entity}
onChanged={testing.fn()}
onError={testing.fn()}
/>,
);

// Check table structure
screen.getByText('Name');
Expand Down Expand Up @@ -163,7 +187,13 @@ describe('EntityTags tests', () => {
});
const {render} = rendererWith({capabilities: true, gmp});

render(<EntityTags entity={entity} />);
render(
<EntityTags
entity={entity}
onChanged={testing.fn()}
onError={testing.fn()}
/>,
);

const editIcons = screen.getAllByTitle('Edit Tag');
fireEvent.click(editIcons[0]);
Expand All @@ -185,7 +215,13 @@ describe('EntityTags tests', () => {

const {render} = rendererWith({gmp, capabilities: true});

render(<EntityTags entity={entity} onChanged={handleChanged} />);
render(
<EntityTags
entity={entity}
onChanged={handleChanged}
onError={testing.fn()}
/>,
);

const removeIcons = screen.getAllByTestId('trashcan-icon');
fireEvent.click(removeIcons[0]);
Expand Down
2 changes: 1 addition & 1 deletion src/web/hooks/usePreviousValue.ts
Original file line number Diff line number Diff line change
Expand Up @@ -22,7 +22,7 @@ import {useEffect, useRef} from 'react';
* ```
*/
const usePreviousValue = <TValue>(value: TValue) => {
const ref = useRef<TValue>(); // initially the previous value is undefined
const ref = useRef<TValue | undefined>(undefined); // initially the previous value is undefined

useEffect(() => {
// will be called AFTER the calling component has rendered
Expand Down
3 changes: 3 additions & 0 deletions src/web/pages/audits/DetailsPage.tsx
Original file line number Diff line number Diff line change
Expand Up @@ -172,12 +172,15 @@ const AuditDetailsPage = () => {
<AuditComponent
onCloneError={onError}
onCloned={goToDetails('audit', navigate)}
onCreateError={onError}
onCreated={onChanged}
onDeleteError={onError}
onDeleted={goToList('audits', navigate)}
onDownloadError={onError}
onDownloaded={onDownloaded}
onResumeError={onError}
onResumed={onChanged}
onSaveError={onError}
onSaved={onChanged}
onStartError={onError}
onStarted={onChanged}
Expand Down
Loading
Loading