--- /dev/null
+/*
+ * SonarQube
+ * Copyright (C) 2009-2022 SonarSource SA
+ * mailto:info AT sonarsource DOT com
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 3 of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public License
+ * along with this program; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ */
+import { cloneDeep, pick, range, times } from 'lodash';
+import { mockHotspot, mockRawHotspot } from '../../helpers/mocks/security-hotspots';
+import { mockSourceLine } from '../../helpers/mocks/sources';
+import { mockRuleDetails } from '../../helpers/testMocks';
+import { BranchParameters } from '../../types/branch-like';
+import { Hotspot, HotspotResolution, HotspotStatus } from '../../types/security-hotspots';
+import { getSources } from '../components';
+import { getMeasures } from '../measures';
+import { getRuleDetails } from '../rules';
+import { getSecurityHotspotDetails, getSecurityHotspots } from '../security-hotspots';
+
+const NUMBER_OF_LINES = 20;
+const MAX_END_RANGE = 10;
+
+export default class SecurityHotspotServiceMock {
+ hotspots: Hotspot[];
+ rawHotspotKey: string[];
+
+ constructor() {
+ this.rawHotspotKey = Object.keys(mockRawHotspot());
+ this.hotspots = [
+ mockHotspot({ key: '1', status: HotspotStatus.TO_REVIEW }),
+ mockHotspot({ key: '2', status: HotspotStatus.TO_REVIEW })
+ ];
+
+ (getMeasures as jest.Mock).mockImplementation(this.handleGetMeasures);
+ (getSecurityHotspots as jest.Mock).mockImplementation(this.handleGetSecurityHotspots);
+ (getSecurityHotspotDetails as jest.Mock).mockImplementation(
+ this.handleGetSecurityHotspotDetails
+ );
+ (getRuleDetails as jest.Mock).mockResolvedValue({ rule: mockRuleDetails() });
+ (getSources as jest.Mock).mockResolvedValue(
+ times(NUMBER_OF_LINES, n =>
+ mockSourceLine({
+ line: n,
+ code: ' <span class="sym-35 sym">symbole</span>'
+ })
+ )
+ );
+ }
+
+ handleGetSources = (data: { key: string; from?: number; to?: number } & BranchParameters) => {
+ return this.reply(
+ range(data.from || 1, data.to || MAX_END_RANGE).map(line => mockSourceLine({ line }))
+ );
+ };
+
+ handleGetSecurityHotspots = (
+ data: {
+ projectKey: string;
+ p: number;
+ ps: number;
+ status?: HotspotStatus;
+ resolution?: HotspotResolution;
+ onlyMine?: boolean;
+ inNewCodePeriod?: boolean;
+ } & BranchParameters
+ ) => {
+ return this.reply({
+ paging: { pageIndex: 1, pageSize: data.ps, total: this.hotspots.length },
+ hotspots: this.hotspots.map(hotspot => pick(hotspot, this.rawHotspotKey)),
+ components: [
+ {
+ key: 'guillaume-peoch-sonarsource_benflix_AYGpXq2bd8qy4i0eO9ed:index.php',
+ qualifier: 'FIL',
+ name: 'index.php',
+ longName: 'index.php',
+ path: 'index.php'
+ },
+ {
+ key: 'guillaume-peoch-sonarsource_benflix_AYGpXq2bd8qy4i0eO9ed',
+ qualifier: 'TRK',
+ name: 'benflix',
+ longName: 'benflix'
+ }
+ ]
+ });
+ };
+
+ handleGetSecurityHotspotDetails = (securityHotspotKey: string) => {
+ const hotspot = this.hotspots.find(h => h.key === securityHotspotKey);
+
+ if (hotspot === undefined) {
+ return Promise.reject({
+ errors: [{ msg: `No security hotspot for key ${securityHotspotKey}` }]
+ });
+ }
+
+ return this.reply(hotspot);
+ };
+
+ handleGetMeasures = () => {
+ return this.reply([
+ {
+ component: {
+ key: 'guillaume-peoch-sonarsource_benflix_AYGpXq2bd8qy4i0eO9ed',
+ name: 'benflix',
+ qualifier: 'TRK',
+ measures: [{ metric: 'security_hotspots_reviewed', value: '0.0', bestValue: false }]
+ }
+ }
+ ]);
+ };
+
+ reply<T>(response: T): Promise<T> {
+ return Promise.resolve(cloneDeep(response));
+ }
+
+ reset = () => {
+ this.rawHotspotKey = Object.keys(mockRawHotspot());
+ this.hotspots = [
+ mockHotspot({ key: '1', status: HotspotStatus.TO_REVIEW }),
+ mockHotspot({ key: '2', status: HotspotStatus.TO_REVIEW })
+ ];
+ };
+}
--- /dev/null
+/*
+ * SonarQube
+ * Copyright (C) 2009-2022 SonarSource SA
+ * mailto:info AT sonarsource DOT com
+ *
+ * This program is free software; you can redistribute it and/or
+ * modify it under the terms of the GNU Lesser General Public
+ * License as published by the Free Software Foundation; either
+ * version 3 of the License, or (at your option) any later version.
+ *
+ * This program is distributed in the hope that it will be useful,
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
+ * Lesser General Public License for more details.
+ *
+ * You should have received a copy of the GNU Lesser General Public License
+ * along with this program; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
+ */
+import { screen, within } from '@testing-library/react';
+import userEvent from '@testing-library/user-event';
+import React from 'react';
+import { Route } from 'react-router-dom';
+import { byRole, byTestId } from 'testing-library-selector';
+import SecurityHotspotServiceMock from '../../../api/mocks/SecurityHotspotServiceMock';
+import { mockComponent } from '../../../helpers/mocks/component';
+import { mockLoggedInUser } from '../../../helpers/testMocks';
+import { renderAppWithComponentContext } from '../../../helpers/testReactTestingUtils';
+import SecurityHotspotsApp from '../SecurityHotspotsApp';
+
+jest.mock('../../../api/measures');
+jest.mock('../../../api/security-hotspots');
+jest.mock('../../../api/rules');
+jest.mock('../../../api/components');
+
+const ui = {
+ selectStatusButton: byRole('button', {
+ name: 'hotspots.status.select_status'
+ }),
+ panel: byTestId('security-hotspot-test')
+};
+
+let handler: SecurityHotspotServiceMock;
+
+beforeEach(() => {
+ handler = new SecurityHotspotServiceMock();
+});
+
+afterEach(() => {
+ handler.reset();
+});
+
+it('should remember the comment when toggling change status panel for the same security hotspot', async () => {
+ const user = userEvent.setup();
+ renderSecurityHotspotsApp();
+
+ await user.click(await ui.selectStatusButton.find());
+
+ const comment = 'This is a comment';
+
+ const commentSection = within(ui.panel.get()).getByRole('textbox');
+ await user.click(commentSection);
+ await user.keyboard(comment);
+
+ // Close the panel
+ await user.keyboard('{Escape}');
+ // Check panel is closed
+ expect(ui.panel.query()).not.toBeInTheDocument();
+
+ await user.click(await ui.selectStatusButton.find());
+
+ expect(await screen.findByText(comment)).toBeInTheDocument();
+});
+
+function renderSecurityHotspotsApp(navigateTo?: string) {
+ renderAppWithComponentContext(
+ 'security_hotspots',
+ () => <Route path="security_hotspots" element={<SecurityHotspotsApp />} />,
+ {
+ navigateTo,
+ currentUser: mockLoggedInUser({
+ login: 'foo',
+ name: 'foo'
+ })
+ },
+ {
+ branchLikes: [],
+ onBranchesChange: jest.fn(),
+ onComponentChange: jest.fn(),
+ component: mockComponent({
+ key: 'guillaume-peoch-sonarsource_benflix_AYGpXq2bd8qy4i0eO9ed',
+ name: 'benflix'
+ })
+ }
+ );
+}
export function Status(props: StatusProps) {
const { currentUser, hotspot } = props;
+
const [isOpen, setIsOpen] = React.useState(false);
+ const [comment, setComment] = React.useState('');
+
+ React.useEffect(() => {
+ setComment('');
+ }, [hotspot.key]);
const statusOption = getStatusOptionFromStatusAndResolution(hotspot.status, hotspot.resolution);
const readonly = !hotspot.canChangeStatus || !isLoggedIn(currentUser);
await props.onStatusChange(status);
setIsOpen(false);
}}
+ comment={comment}
+ setComment={setComment}
/>
</DropdownOverlay>
}>
interface Props {
hotspot: Hotspot;
onStatusOptionChange: (statusOption: HotspotStatusOption) => Promise<void>;
+ comment: string;
+ setComment: (comment: string) => void;
}
interface State {
- comment?: string;
loading: boolean;
initialStatus: HotspotStatusOption;
selectedStatus: HotspotStatusOption;
};
handleCommentChange = (comment: string) => {
- this.setState({ comment });
+ this.props.setComment(comment);
};
handleSubmit = () => {
- const { hotspot } = this.props;
- const { comment, initialStatus, selectedStatus } = this.state;
+ const { hotspot, comment } = this.props;
+ const { initialStatus, selectedStatus } = this.state;
if (selectedStatus && selectedStatus !== initialStatus) {
this.setState({ loading: true });
})
.then(async () => {
await this.props.onStatusOptionChange(selectedStatus);
- this.setState({ loading: false });
+ if (this.mounted) {
+ this.setState({ loading: false });
+ }
})
.catch(() => this.setState({ loading: false }));
}
};
render() {
- const { comment, initialStatus, loading, selectedStatus } = this.state;
+ const { comment } = this.props;
+ const { initialStatus, loading, selectedStatus } = this.state;
const submitDisabled = selectedStatus === initialStatus;
return (
};
return (
- <div className="abs-width-400">
+ <div data-testid="security-hotspot-test" className="abs-width-400">
<div className="big-padded">
{renderOption(HotspotStatusOption.TO_REVIEW)}
{renderOption(HotspotStatusOption.ACKNOWLEDGED)}
* along with this program; if not, write to the Free Software Foundation,
* Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
*/
-import { shallow } from 'enzyme';
import * as React from 'react';
-import { DropdownOverlay } from '../../../../../components/controls/Dropdown';
-import Toggler from '../../../../../components/controls/Toggler';
import { mockHotspot } from '../../../../../helpers/mocks/security-hotspots';
import { mockCurrentUser } from '../../../../../helpers/testMocks';
-import { click } from '../../../../../helpers/testUtils';
-import { HotspotStatusOption } from '../../../../../types/security-hotspots';
import { Status, StatusProps } from '../Status';
-import StatusSelection from '../StatusSelection';
-it('should render correctly', () => {
- const wrapper = shallowRender();
- expect(wrapper).toMatchSnapshot('closed');
+import { render, screen } from '@testing-library/react';
+import userEvent from '@testing-library/user-event';
+import { setSecurityHotspotStatus } from '../../../../../api/security-hotspots';
+import { HotspotResolution, HotspotStatus } from '../../../../../types/security-hotspots';
- click(wrapper.find('#status-trigger'));
- expect(wrapper).toMatchSnapshot('open');
+jest.mock('../../../../../api/security-hotspots', () => ({
+ setSecurityHotspotStatus: jest.fn().mockResolvedValue({})
+}));
- wrapper
- .find(Toggler)
- .props()
- .onRequestClose();
- expect(wrapper.find(DropdownOverlay).length).toBe(0);
+it('should properly deal with comment/status/submit events', async () => {
+ const hotspot = mockHotspot();
+ renderStatusSelection({ hotspot });
+ const user = userEvent.setup();
+ const comment = 'COMMENT-TEXT';
- expect(shallowRender({ hotspot: mockHotspot({ canChangeStatus: false }) })).toMatchSnapshot(
- 'readonly'
+ await user.click(screen.getByRole('button', { name: 'hotspots.status.select_status' }));
+
+ await user.click(
+ screen.getByRole('radio', {
+ name: 'hotspots.status_option.SAFE hotspots.status_option.SAFE.description'
+ })
);
+
+ await user.click(screen.getByRole('textbox'));
+ await user.keyboard(comment);
+
+ await user.click(screen.getByRole('button', { name: 'hotspots.status.change_status' }));
+
+ expect(setSecurityHotspotStatus).toBeCalledWith(hotspot.key, {
+ status: HotspotStatus.REVIEWED,
+ resolution: HotspotResolution.SAFE,
+ comment
+ });
});
-it('should properly deal with status changes', () => {
- const onStatusChange = jest.fn();
- const wrapper = shallowRender({ onStatusChange });
+it('should open change status panel correctly', async () => {
+ renderStatusSelection();
+ const user = userEvent.setup();
+ expect(screen.queryByTestId('security-hotspot-test')).not.toBeInTheDocument();
+ await user.click(screen.getByRole('button', { name: 'hotspots.status.select_status' }));
+ expect(screen.getByTestId('security-hotspot-test')).toBeInTheDocument();
+});
+
+it('should disallow status change for hotspot that are readonly', () => {
+ renderStatusSelection({ hotspot: mockHotspot({ canChangeStatus: false }) });
+ expect(screen.getByRole('button')).toBeDisabled();
+});
- click(wrapper.find('#status-trigger'));
- wrapper
- .find(Toggler)
- .dive()
- .find(StatusSelection)
- .props()
- .onStatusOptionChange(HotspotStatusOption.SAFE);
- expect(onStatusChange).toHaveBeenCalled();
- expect(wrapper.find(DropdownOverlay).length).toBe(0);
+it('should disallow status change for user that are not logged in', () => {
+ renderStatusSelection({ currentUser: mockCurrentUser({ isLoggedIn: false }) });
+ expect(screen.getByRole('button')).toBeDisabled();
});
-function shallowRender(props?: Partial<StatusProps>) {
- return shallow<StatusProps>(
+function renderStatusSelection(props?: Partial<StatusProps>) {
+ render(
<Status
currentUser={mockCurrentUser({ isLoggedIn: true })}
hotspot={mockHotspot()}
+++ /dev/null
-/*
- * SonarQube
- * Copyright (C) 2009-2022 SonarSource SA
- * mailto:info AT sonarsource DOT com
- *
- * This program is free software; you can redistribute it and/or
- * modify it under the terms of the GNU Lesser General Public
- * License as published by the Free Software Foundation; either
- * version 3 of the License, or (at your option) any later version.
- *
- * This program is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- * Lesser General Public License for more details.
- *
- * You should have received a copy of the GNU Lesser General Public License
- * along with this program; if not, write to the Free Software Foundation,
- * Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
- */
-import { shallow } from 'enzyme';
-import * as React from 'react';
-import { setSecurityHotspotStatus } from '../../../../../api/security-hotspots';
-import { mockHotspot } from '../../../../../helpers/mocks/security-hotspots';
-import { waitAndUpdate } from '../../../../../helpers/testUtils';
-import { HotspotStatus, HotspotStatusOption } from '../../../../../types/security-hotspots';
-import StatusSelection from '../StatusSelection';
-import StatusSelectionRenderer from '../StatusSelectionRenderer';
-
-jest.mock('../../../../../api/security-hotspots', () => ({
- setSecurityHotspotStatus: jest.fn()
-}));
-
-it('should render correctly', () => {
- expect(shallowRender()).toMatchSnapshot();
-});
-
-it('should properly deal with comment/status/submit events', async () => {
- const hotspot = mockHotspot();
- const onStatusOptionChange = jest.fn();
- const wrapper = shallowRender({ hotspot, onStatusOptionChange });
-
- const newStatusOption = HotspotStatusOption.SAFE;
- wrapper
- .find(StatusSelectionRenderer)
- .props()
- .onStatusChange(newStatusOption);
- expect(wrapper.state().selectedStatus).toBe(newStatusOption);
- expect(wrapper.find(StatusSelectionRenderer).props().submitDisabled).toBe(false);
-
- const newComment = 'TEST-COMMENT';
- wrapper
- .find(StatusSelectionRenderer)
- .props()
- .onCommentChange(newComment);
- expect(wrapper.state().comment).toBe(newComment);
-
- (setSecurityHotspotStatus as jest.Mock).mockResolvedValueOnce({});
- wrapper
- .find(StatusSelectionRenderer)
- .props()
- .onSubmit();
- expect(setSecurityHotspotStatus).toHaveBeenCalledWith(hotspot.key, {
- status: HotspotStatus.REVIEWED,
- resolution: HotspotStatusOption.SAFE,
- comment: newComment
- });
-
- await waitAndUpdate(wrapper);
-
- expect(onStatusOptionChange).toHaveBeenCalledWith(newStatusOption);
-});
-
-function shallowRender(props?: Partial<StatusSelection['props']>) {
- return shallow<StatusSelection>(
- <StatusSelection hotspot={mockHotspot()} onStatusOptionChange={jest.fn()} {...props} />
- );
-}
+++ /dev/null
-/*
- * SonarQube
- * Copyright (C) 2009-2022 SonarSource SA
- * mailto:info AT sonarsource DOT com
- *
- * This program is free software; you can redistribute it and/or
- * modify it under the terms of the GNU Lesser General Public
- * License as published by the Free Software Foundation; either
- * version 3 of the License, or (at your option) any later version.
- *
- * This program is distributed in the hope that it will be useful,
- * but WITHOUT ANY WARRANTY; without even the implied warranty of
- * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
- * Lesser General Public License for more details.
- *
- * You should have received a copy of the GNU Lesser General Public License
- * along with this program; if not, write to the Free Software Foundation,
- * Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA.
- */
-import { shallow } from 'enzyme';
-import * as React from 'react';
-import { SubmitButton } from '../../../../../components/controls/buttons';
-import Radio from '../../../../../components/controls/Radio';
-import { change, click } from '../../../../../helpers/testUtils';
-import { HotspotStatusOption } from '../../../../../types/security-hotspots';
-import StatusSelectionRenderer, { StatusSelectionRendererProps } from '../StatusSelectionRenderer';
-
-it('should render correctly', () => {
- expect(shallowRender()).toMatchSnapshot();
- expect(shallowRender({ loading: true })).toMatchSnapshot('loading');
- expect(
- shallowRender({ submitDisabled: true })
- .find(SubmitButton)
- .props().disabled
- ).toBe(true);
-});
-
-it('should call proper callbacks on actions', () => {
- const onCommentChange = jest.fn();
- const onStatusChange = jest.fn();
- const onSubmit = jest.fn();
- const wrapper = shallowRender({ onCommentChange, onStatusChange, onSubmit });
-
- change(wrapper.find('textarea'), 'TATA');
- expect(onCommentChange).toHaveBeenCalledWith('TATA');
-
- wrapper
- .find(Radio)
- .first()
- .props()
- .onCheck(HotspotStatusOption.SAFE);
- expect(onStatusChange).toHaveBeenCalledWith(HotspotStatusOption.SAFE);
-
- click(wrapper.find(SubmitButton));
- expect(onSubmit).toHaveBeenCalled();
-});
-
-function shallowRender(props?: Partial<StatusSelectionRendererProps>) {
- return shallow<StatusSelectionRendererProps>(
- <StatusSelectionRenderer
- comment="TEST-COMMENT"
- loading={false}
- onCommentChange={jest.fn()}
- onStatusChange={jest.fn()}
- onSubmit={jest.fn()}
- selectedStatus={HotspotStatusOption.TO_REVIEW}
- submitDisabled={false}
- {...props}
- />
- );
-}
+++ /dev/null
-// Jest Snapshot v1, https://goo.gl/fbAQLP
-
-exports[`should render correctly: closed 1`] = `
-<div
- className="display-flex-row display-flex-end"
->
- <StatusDescription
- showTitle={true}
- statusOption="FIXED"
- />
- <div
- className="spacer-top"
- >
- <Tooltip
- overlay={null}
- placement="bottom"
- >
- <div
- className="dropdown"
- >
- <Toggler
- closeOnClickOutside={true}
- closeOnEscape={true}
- onRequestClose={[Function]}
- open={false}
- overlay={
- <DropdownOverlay
- noPadding={true}
- placement="bottom"
- >
- <StatusSelection
- hotspot={
- Object {
- "assignee": "assignee",
- "assigneeUser": Object {
- "active": true,
- "local": true,
- "login": "assignee",
- "name": "John Doe",
- },
- "author": "author",
- "authorUser": Object {
- "active": true,
- "local": true,
- "login": "author",
- "name": "John Doe",
- },
- "canChangeStatus": true,
- "changelog": Array [],
- "comment": Array [],
- "component": Object {
- "key": "hotspot-component",
- "longName": "Hotspot component long name",
- "name": "Hotspot Component",
- "path": "path/to/component",
- "qualifier": "FIL",
- },
- "creationDate": "2013-05-13T17:55:41+0200",
- "flows": Array [
- Object {
- "locations": Array [
- Object {
- "component": "main.js",
- "textRange": Object {
- "endLine": 2,
- "endOffset": 2,
- "startLine": 1,
- "startOffset": 1,
- },
- },
- ],
- },
- ],
- "key": "01fc972e-2a3c-433e-bcae-0bd7f88f5123",
- "line": 142,
- "message": "'3' is a magic number.",
- "project": Object {
- "key": "hotspot-component",
- "longName": "Hotspot component long name",
- "name": "Hotspot Component",
- "path": "path/to/component",
- "qualifier": "TRK",
- },
- "resolution": "FIXED",
- "rule": Object {
- "key": "squid:S2077",
- "name": "That rule",
- "securityCategory": "sql-injection",
- "vulnerabilityProbability": "HIGH",
- },
- "status": "REVIEWED",
- "textRange": Object {
- "endLine": 142,
- "endOffset": 83,
- "startLine": 142,
- "startOffset": 26,
- },
- "updateDate": "2013-05-13T17:55:42+0200",
- "users": Array [
- Object {
- "active": true,
- "local": true,
- "login": "assignee",
- "name": "John Doe",
- },
- Object {
- "active": true,
- "local": true,
- "login": "author",
- "name": "John Doe",
- },
- ],
- }
- }
- onStatusOptionChange={[Function]}
- />
- </DropdownOverlay>
- }
- >
- <Button
- className="dropdown-toggle big-spacer-left"
- disabled={false}
- id="status-trigger"
- onClick={[Function]}
- >
- <span>
- hotspots.status.select_status
- </span>
- <DropdownIcon
- className="little-spacer-left"
- />
- </Button>
- </Toggler>
- </div>
- </Tooltip>
- </div>
-</div>
-`;
-
-exports[`should render correctly: open 1`] = `
-<div
- className="display-flex-row display-flex-end"
->
- <StatusDescription
- showTitle={true}
- statusOption="FIXED"
- />
- <div
- className="spacer-top"
- >
- <Tooltip
- overlay={null}
- placement="bottom"
- >
- <div
- className="dropdown"
- >
- <Toggler
- closeOnClickOutside={true}
- closeOnEscape={true}
- onRequestClose={[Function]}
- open={true}
- overlay={
- <DropdownOverlay
- noPadding={true}
- placement="bottom"
- >
- <StatusSelection
- hotspot={
- Object {
- "assignee": "assignee",
- "assigneeUser": Object {
- "active": true,
- "local": true,
- "login": "assignee",
- "name": "John Doe",
- },
- "author": "author",
- "authorUser": Object {
- "active": true,
- "local": true,
- "login": "author",
- "name": "John Doe",
- },
- "canChangeStatus": true,
- "changelog": Array [],
- "comment": Array [],
- "component": Object {
- "key": "hotspot-component",
- "longName": "Hotspot component long name",
- "name": "Hotspot Component",
- "path": "path/to/component",
- "qualifier": "FIL",
- },
- "creationDate": "2013-05-13T17:55:41+0200",
- "flows": Array [
- Object {
- "locations": Array [
- Object {
- "component": "main.js",
- "textRange": Object {
- "endLine": 2,
- "endOffset": 2,
- "startLine": 1,
- "startOffset": 1,
- },
- },
- ],
- },
- ],
- "key": "01fc972e-2a3c-433e-bcae-0bd7f88f5123",
- "line": 142,
- "message": "'3' is a magic number.",
- "project": Object {
- "key": "hotspot-component",
- "longName": "Hotspot component long name",
- "name": "Hotspot Component",
- "path": "path/to/component",
- "qualifier": "TRK",
- },
- "resolution": "FIXED",
- "rule": Object {
- "key": "squid:S2077",
- "name": "That rule",
- "securityCategory": "sql-injection",
- "vulnerabilityProbability": "HIGH",
- },
- "status": "REVIEWED",
- "textRange": Object {
- "endLine": 142,
- "endOffset": 83,
- "startLine": 142,
- "startOffset": 26,
- },
- "updateDate": "2013-05-13T17:55:42+0200",
- "users": Array [
- Object {
- "active": true,
- "local": true,
- "login": "assignee",
- "name": "John Doe",
- },
- Object {
- "active": true,
- "local": true,
- "login": "author",
- "name": "John Doe",
- },
- ],
- }
- }
- onStatusOptionChange={[Function]}
- />
- </DropdownOverlay>
- }
- >
- <Button
- className="dropdown-toggle big-spacer-left"
- disabled={false}
- id="status-trigger"
- onClick={[Function]}
- >
- <span>
- hotspots.status.select_status
- </span>
- <DropdownIcon
- className="little-spacer-left"
- />
- </Button>
- </Toggler>
- </div>
- </Tooltip>
- </div>
-</div>
-`;
-
-exports[`should render correctly: readonly 1`] = `
-<div
- className="display-flex-row display-flex-end"
->
- <StatusDescription
- showTitle={true}
- statusOption="FIXED"
- />
- <div
- className="spacer-top"
- >
- <Tooltip
- overlay="hotspots.status.cannot_change_status"
- placement="bottom"
- >
- <div
- className="dropdown"
- >
- <Toggler
- closeOnClickOutside={true}
- closeOnEscape={true}
- onRequestClose={[Function]}
- open={false}
- overlay={
- <DropdownOverlay
- noPadding={true}
- placement="bottom"
- >
- <StatusSelection
- hotspot={
- Object {
- "assignee": "assignee",
- "assigneeUser": Object {
- "active": true,
- "local": true,
- "login": "assignee",
- "name": "John Doe",
- },
- "author": "author",
- "authorUser": Object {
- "active": true,
- "local": true,
- "login": "author",
- "name": "John Doe",
- },
- "canChangeStatus": false,
- "changelog": Array [],
- "comment": Array [],
- "component": Object {
- "key": "hotspot-component",
- "longName": "Hotspot component long name",
- "name": "Hotspot Component",
- "path": "path/to/component",
- "qualifier": "FIL",
- },
- "creationDate": "2013-05-13T17:55:41+0200",
- "flows": Array [
- Object {
- "locations": Array [
- Object {
- "component": "main.js",
- "textRange": Object {
- "endLine": 2,
- "endOffset": 2,
- "startLine": 1,
- "startOffset": 1,
- },
- },
- ],
- },
- ],
- "key": "01fc972e-2a3c-433e-bcae-0bd7f88f5123",
- "line": 142,
- "message": "'3' is a magic number.",
- "project": Object {
- "key": "hotspot-component",
- "longName": "Hotspot component long name",
- "name": "Hotspot Component",
- "path": "path/to/component",
- "qualifier": "TRK",
- },
- "resolution": "FIXED",
- "rule": Object {
- "key": "squid:S2077",
- "name": "That rule",
- "securityCategory": "sql-injection",
- "vulnerabilityProbability": "HIGH",
- },
- "status": "REVIEWED",
- "textRange": Object {
- "endLine": 142,
- "endOffset": 83,
- "startLine": 142,
- "startOffset": 26,
- },
- "updateDate": "2013-05-13T17:55:42+0200",
- "users": Array [
- Object {
- "active": true,
- "local": true,
- "login": "assignee",
- "name": "John Doe",
- },
- Object {
- "active": true,
- "local": true,
- "login": "author",
- "name": "John Doe",
- },
- ],
- }
- }
- onStatusOptionChange={[Function]}
- />
- </DropdownOverlay>
- }
- >
- <Button
- className="dropdown-toggle big-spacer-left"
- disabled={true}
- id="status-trigger"
- onClick={[Function]}
- >
- <span>
- hotspots.status.select_status
- </span>
- <DropdownIcon
- className="little-spacer-left"
- />
- </Button>
- </Toggler>
- </div>
- </Tooltip>
- </div>
-</div>
-`;
+++ /dev/null
-// Jest Snapshot v1, https://goo.gl/fbAQLP
-
-exports[`should render correctly 1`] = `
-<StatusSelectionRenderer
- loading={false}
- onCommentChange={[Function]}
- onStatusChange={[Function]}
- onSubmit={[Function]}
- selectedStatus="FIXED"
- submitDisabled={true}
-/>
-`;
+++ /dev/null
-// Jest Snapshot v1, https://goo.gl/fbAQLP
-
-exports[`should render correctly 1`] = `
-<div
- className="abs-width-400"
->
- <div
- className="big-padded"
- >
- <Radio
- alignLabel={true}
- checked={true}
- className="big-spacer-bottom status-radio"
- onCheck={[MockFunction]}
- value="TO_REVIEW"
- >
- <StatusDescription
- statusInBadge={false}
- statusOption="TO_REVIEW"
- />
- </Radio>
- <Radio
- alignLabel={true}
- checked={false}
- className="big-spacer-bottom status-radio"
- onCheck={[MockFunction]}
- value="ACKNOWLEDGED"
- >
- <StatusDescription
- statusInBadge={false}
- statusOption="ACKNOWLEDGED"
- />
- </Radio>
- <Radio
- alignLabel={true}
- checked={false}
- className="big-spacer-bottom status-radio"
- onCheck={[MockFunction]}
- value="FIXED"
- >
- <StatusDescription
- statusInBadge={false}
- statusOption="FIXED"
- />
- </Radio>
- <Radio
- alignLabel={true}
- checked={false}
- className="big-spacer-bottom status-radio"
- onCheck={[MockFunction]}
- value="SAFE"
- >
- <StatusDescription
- statusInBadge={false}
- statusOption="SAFE"
- />
- </Radio>
- </div>
- <hr />
- <div
- className="big-padded display-flex-column"
- >
- <label
- className="text-bold"
- htmlFor="comment-textarea"
- >
- hotspots.status.add_comment
- </label>
- <textarea
- className="spacer-top form-field fixed-width spacer-bottom"
- id="comment-textarea"
- onChange={[Function]}
- rows={4}
- value="TEST-COMMENT"
- />
- <FormattingTips />
- <div
- className="big-spacer-top display-flex-justify-end display-flex-center"
- >
- <SubmitButton
- disabled={false}
- onClick={[MockFunction]}
- >
- hotspots.status.change_status
- </SubmitButton>
- </div>
- </div>
-</div>
-`;
-
-exports[`should render correctly: loading 1`] = `
-<div
- className="abs-width-400"
->
- <div
- className="big-padded"
- >
- <Radio
- alignLabel={true}
- checked={true}
- className="big-spacer-bottom status-radio"
- onCheck={[MockFunction]}
- value="TO_REVIEW"
- >
- <StatusDescription
- statusInBadge={false}
- statusOption="TO_REVIEW"
- />
- </Radio>
- <Radio
- alignLabel={true}
- checked={false}
- className="big-spacer-bottom status-radio"
- onCheck={[MockFunction]}
- value="ACKNOWLEDGED"
- >
- <StatusDescription
- statusInBadge={false}
- statusOption="ACKNOWLEDGED"
- />
- </Radio>
- <Radio
- alignLabel={true}
- checked={false}
- className="big-spacer-bottom status-radio"
- onCheck={[MockFunction]}
- value="FIXED"
- >
- <StatusDescription
- statusInBadge={false}
- statusOption="FIXED"
- />
- </Radio>
- <Radio
- alignLabel={true}
- checked={false}
- className="big-spacer-bottom status-radio"
- onCheck={[MockFunction]}
- value="SAFE"
- >
- <StatusDescription
- statusInBadge={false}
- statusOption="SAFE"
- />
- </Radio>
- </div>
- <hr />
- <div
- className="big-padded display-flex-column"
- >
- <label
- className="text-bold"
- htmlFor="comment-textarea"
- >
- hotspots.status.add_comment
- </label>
- <textarea
- className="spacer-top form-field fixed-width spacer-bottom"
- id="comment-textarea"
- onChange={[Function]}
- rows={4}
- value="TEST-COMMENT"
- />
- <FormattingTips />
- <div
- className="big-spacer-top display-flex-justify-end display-flex-center"
- >
- <SubmitButton
- disabled={true}
- onClick={[MockFunction]}
- >
- hotspots.status.change_status
- </SubmitButton>
- <i
- className="spacer-left spinner"
- />
- </div>
- </div>
-</div>
-`;