diff options
10 files changed, 428 insertions, 284 deletions
diff --git a/server/sonar-web/src/main/js/apps/projects/components/ProjectCardContainer.js b/server/sonar-web/src/main/js/apps/projects/components/ProjectCardContainer.js index d3908234509..9e71d2559ba 100644 --- a/server/sonar-web/src/main/js/apps/projects/components/ProjectCardContainer.js +++ b/server/sonar-web/src/main/js/apps/projects/components/ProjectCardContainer.js @@ -17,10 +17,19 @@ * along with this program; if not, write to the Free Software Foundation, * Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301, USA. */ +import React from 'react'; import { connect } from 'react-redux'; -import ProjectCard from './ProjectCard'; +import ProjectCardLeak from './ProjectCardLeak'; +import ProjectCardOverall from './ProjectCardOverall'; import { getComponent, getComponentMeasures } from '../../../store/rootReducer'; +function ProjectCard(props: { type?: string }) { + if (props.type === 'leak') { + return <ProjectCardLeak {...props} />; + } + return <ProjectCardOverall {...props} />; +} + export default connect((state, ownProps) => ({ project: getComponent(state, ownProps.projectKey), measures: getComponentMeasures(state, ownProps.projectKey) diff --git a/server/sonar-web/src/main/js/apps/projects/components/ProjectCard.js b/server/sonar-web/src/main/js/apps/projects/components/ProjectCardLeak.js index 94c65bd4a6f..9e38e2bcb2d 100644 --- a/server/sonar-web/src/main/js/apps/projects/components/ProjectCard.js +++ b/server/sonar-web/src/main/js/apps/projects/components/ProjectCardLeak.js @@ -24,7 +24,6 @@ import moment from 'moment'; import { Link } from 'react-router'; import ProjectCardQualityGate from './ProjectCardQualityGate'; import ProjectCardLeakMeasures from './ProjectCardLeakMeasures'; -import ProjectCardOverallMeasures from './ProjectCardOverallMeasures'; import FavoriteContainer from '../../../components/controls/FavoriteContainer'; import Organization from '../../../components/shared/Organization'; import TagsList from '../../../components/tags/TagsList'; @@ -43,11 +42,10 @@ type Props = { isFavorite?: boolean, organization?: string, visibility?: boolean - }, - type?: string + } }; -export default function ProjectCard({ measures, organization, project, type }: Props) { +export default function ProjectCardLeak({ measures, organization, project }: Props) { if (project == null) { return null; } @@ -56,23 +54,15 @@ export default function ProjectCard({ measures, organization, project, type }: P const isPrivate = project.visibility === 'private'; const hasLeakPeriodStart = project.leakPeriodDate != null; const hasTags = project.tags.length > 0; - const isLeakView = type === 'leak'; + const showOrganization = organization == null && project.organization != null; - let areProjectMeasuresLoaded; // check for particular measures because only some measures can be loaded // if coming from visualizations tab - if (isLeakView) { - areProjectMeasuresLoaded = measures != null && measures['new_bugs']; - } else { - areProjectMeasuresLoaded = - measures != null && - measures['reliability_rating'] != null && - measures['sqale_rating'] != null; - } + const areProjectMeasuresLoaded = measures != null && measures['new_bugs']; const displayQualityGate = areProjectMeasuresLoaded && isProjectAnalyzed; const className = classNames('boxed-group', 'project-card', { - 'boxed-group-loading': isProjectAnalyzed && !areProjectMeasuresLoaded + 'boxed-group-loading': isProjectAnalyzed && hasLeakPeriodStart && !areProjectMeasuresLoaded }); return ( @@ -81,8 +71,7 @@ export default function ProjectCard({ measures, organization, project, type }: P {project.isFavorite != null && <FavoriteContainer className="spacer-right" componentKey={project.key} />} <h2 className="project-card-name"> - {organization == null && - project.organization != null && + {showOrganization && <span className="text-normal"> <Organization organizationKey={project.organization} /> </span>} @@ -94,9 +83,9 @@ export default function ProjectCard({ measures, organization, project, type }: P {hasTags && <TagsList tags={project.tags} customClass="spacer-left" />} </div> {isProjectAnalyzed && + hasLeakPeriodStart && <div className="project-card-dates note text-right pull-right"> - {isLeakView && - hasLeakPeriodStart && + {hasLeakPeriodStart && <span> {translateWithParameters( 'projects.leak_period_x', @@ -113,16 +102,15 @@ export default function ProjectCard({ measures, organization, project, type }: P </div>} </div> - {isProjectAnalyzed + {isProjectAnalyzed && hasLeakPeriodStart ? <div className="boxed-group-inner"> - {areProjectMeasuresLoaded && - (isLeakView - ? <ProjectCardLeakMeasures measures={measures} /> - : <ProjectCardOverallMeasures measures={measures} />)} + {areProjectMeasuresLoaded && <ProjectCardLeakMeasures measures={measures} />} </div> : <div className="boxed-group-inner"> <div className="note project-card-not-analyzed"> - {translate('projects.not_analyzed')} + {isProjectAnalyzed + ? translate('projects.no_leak_period') + : translate('projects.not_analyzed')} </div> </div>} </div> diff --git a/server/sonar-web/src/main/js/apps/projects/components/ProjectCardOverall.js b/server/sonar-web/src/main/js/apps/projects/components/ProjectCardOverall.js new file mode 100644 index 00000000000..8ef49b49179 --- /dev/null +++ b/server/sonar-web/src/main/js/apps/projects/components/ProjectCardOverall.js @@ -0,0 +1,106 @@ +/* + * SonarQube + * Copyright (C) 2009-2017 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. + */ +// @flow +import React from 'react'; +import classNames from 'classnames'; +import moment from 'moment'; +import { Link } from 'react-router'; +import ProjectCardQualityGate from './ProjectCardQualityGate'; +import ProjectCardOverallMeasures from './ProjectCardOverallMeasures'; +import FavoriteContainer from '../../../components/controls/FavoriteContainer'; +import Organization from '../../../components/shared/Organization'; +import TagsList from '../../../components/tags/TagsList'; +import PrivateBadge from '../../../components/common/PrivateBadge'; +import { translate, translateWithParameters } from '../../../helpers/l10n'; + +type Props = { + measures: { [string]: string }, + organization?: { key: string }, + project?: { + analysisDate?: string, + key: string, + name: string, + tags: Array<string>, + isFavorite?: boolean, + organization?: string, + visibility?: boolean + } +}; + +export default function ProjectCardOverall({ measures, organization, project }: Props) { + if (project == null) { + return null; + } + + const isProjectAnalyzed = project.analysisDate != null; + const isPrivate = project.visibility === 'private'; + const hasTags = project.tags.length > 0; + const showOrganization = organization == null && project.organization != null; + + // check for particular measures because only some measures can be loaded + // if coming from visualizations tab + const areProjectMeasuresLoaded = + measures != null && measures['reliability_rating'] != null && measures['sqale_rating'] != null; + + const displayQualityGate = areProjectMeasuresLoaded && isProjectAnalyzed; + const className = classNames('boxed-group', 'project-card', { + 'boxed-group-loading': isProjectAnalyzed && !areProjectMeasuresLoaded + }); + + return ( + <div data-key={project.key} className={className}> + <div className="boxed-group-header clearfix"> + {project.isFavorite != null && + <FavoriteContainer className="spacer-right" componentKey={project.key} />} + <h2 className="project-card-name"> + {showOrganization && + <span className="text-normal"> + <Organization organizationKey={project.organization} /> + </span>} + <Link to={{ pathname: '/dashboard', query: { id: project.key } }}>{project.name}</Link> + </h2> + {displayQualityGate && <ProjectCardQualityGate status={measures['alert_status']} />} + <div className="pull-right text-right"> + {isPrivate && <PrivateBadge className="spacer-left" tooltipPlacement="left" />} + {hasTags && <TagsList tags={project.tags} customClass="spacer-left" />} + </div> + {isProjectAnalyzed && + <div className="project-card-dates note text-right pull-right"> + <span className="big-spacer-left"> + {translateWithParameters( + 'projects.last_analysis_on_x', + moment(project.analysisDate).format('LLL') + )} + </span> + </div>} + </div> + + {isProjectAnalyzed + ? <div className="boxed-group-inner"> + {areProjectMeasuresLoaded && <ProjectCardOverallMeasures measures={measures} />} + </div> + : <div className="boxed-group-inner"> + <div className="note project-card-not-analyzed"> + {translate('projects.not_analyzed')} + </div> + </div>} + </div> + ); +} diff --git a/server/sonar-web/src/main/js/apps/projects/components/__tests__/ProjectCard-test.js b/server/sonar-web/src/main/js/apps/projects/components/__tests__/ProjectCard-test.js deleted file mode 100644 index a5e143fb5f0..00000000000 --- a/server/sonar-web/src/main/js/apps/projects/components/__tests__/ProjectCard-test.js +++ /dev/null @@ -1,136 +0,0 @@ -/* - * SonarQube - * Copyright (C) 2009-2017 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 React from 'react'; -import { shallow } from 'enzyme'; -import ProjectCard from '../ProjectCard'; - -const PROJECT = { - analysisDate: '2017-01-01', - leakPeriodDate: '2016-12-01', - key: 'foo', - name: 'Foo', - tags: [] -}; -const MEASURES = { - alert_status: 'OK', - reliability_rating: '1.0', - sqale_rating: '1.0', - new_bugs: 12 -}; - -jest.mock('moment', () => () => ({ - format: () => 'March 1, 2017 9:36 AM', - fromNow: () => 'a month ago' -})); - -describe('overall status project card', () => { - it('should display analysis date (and not leak period) when defined', () => { - expect( - shallow(<ProjectCard measures={{}} project={PROJECT} />).find('.project-card-dates').exists() - ).toBeTruthy(); - expect( - shallow(<ProjectCard measures={{}} project={{ ...PROJECT, analysisDate: undefined }} />) - .find('.project-card-dates') - .exists() - ).toBeFalsy(); - }); - - it('should display loading', () => { - const measures = { ...MEASURES, sqale_rating: undefined }; - expect( - shallow(<ProjectCard project={PROJECT} />) - .find('.boxed-group') - .hasClass('boxed-group-loading') - ).toBeTruthy(); - expect( - shallow(<ProjectCard measures={measures} project={PROJECT} />) - .find('.boxed-group') - .hasClass('boxed-group-loading') - ).toBeTruthy(); - }); - - it('should not display the quality gate', () => { - const project = { ...PROJECT, analysisDate: undefined }; - expect( - shallow(<ProjectCard measures={MEASURES} project={project} />) - .find('ProjectCardQualityGate') - .exists() - ).toBeFalsy(); - }); - - it('should display tags', () => { - const project = { ...PROJECT, tags: ['foo', 'bar'] }; - expect(shallow(<ProjectCard project={project} />).find('TagsList').exists()).toBeTruthy(); - }); - - it('should private badge', () => { - const project = { ...PROJECT, visibility: 'private' }; - expect( - shallow(<ProjectCard type="overall" project={project} />).find('PrivateBadge').exists() - ).toBeTruthy(); - }); - - it('should display the overall measures and quality gate', () => { - expect(shallow(<ProjectCard measures={MEASURES} project={PROJECT} />)).toMatchSnapshot(); - }); -}); - -describe('leak project card', () => { - it('should display analysis date and leak start date', () => { - const card = shallow(<ProjectCard type="leak" measures={MEASURES} project={PROJECT} />); - expect(card.find('.project-card-dates').exists()).toBeTruthy(); - expect(card.find('.project-card-dates').find('span').getNodes()).toHaveLength(2); - }); - - it('should not display analysis date or leak start date', () => { - const project = { ...PROJECT, analysisDate: undefined }; - const card = shallow(<ProjectCard type="leak" measures={MEASURES} project={project} />); - expect(card.find('.project-card-dates').exists()).toBeFalsy(); - }); - - it('should display loading', () => { - const measures = { ...MEASURES, new_bugs: undefined }; - expect( - shallow(<ProjectCard type="leak" measures={measures} project={PROJECT} />) - .find('.boxed-group') - .hasClass('boxed-group-loading') - ).toBeTruthy(); - }); - - it('should display tags', () => { - const project = { ...PROJECT, tags: ['foo', 'bar'] }; - expect( - shallow(<ProjectCard type="leak" project={project} />).find('TagsList').exists() - ).toBeTruthy(); - }); - - it('should private badge', () => { - const project = { ...PROJECT, visibility: 'private' }; - expect( - shallow(<ProjectCard type="leak" project={project} />).find('PrivateBadge').exists() - ).toBeTruthy(); - }); - - it('should display the leak measures and quality gate', () => { - expect( - shallow(<ProjectCard type="leak" measures={MEASURES} project={PROJECT} />) - ).toMatchSnapshot(); - }); -}); diff --git a/server/sonar-web/src/main/js/apps/projects/components/__tests__/ProjectCardLeak-test.js b/server/sonar-web/src/main/js/apps/projects/components/__tests__/ProjectCardLeak-test.js new file mode 100644 index 00000000000..46819f2bd13 --- /dev/null +++ b/server/sonar-web/src/main/js/apps/projects/components/__tests__/ProjectCardLeak-test.js @@ -0,0 +1,82 @@ +/* + * SonarQube + * Copyright (C) 2009-2017 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 React from 'react'; +import { shallow } from 'enzyme'; +import ProjectCardLeak from '../ProjectCardLeak'; + +const PROJECT = { + analysisDate: '2017-01-01', + leakPeriodDate: '2016-12-01', + key: 'foo', + name: 'Foo', + tags: [] +}; +const MEASURES = { + alert_status: 'OK', + reliability_rating: '1.0', + sqale_rating: '1.0', + new_bugs: 12 +}; + +jest.mock('moment', () => () => ({ + format: () => 'March 1, 2017 9:36 AM', + fromNow: () => 'a month ago' +})); + +it('should display analysis date and leak start date', () => { + const card = shallow(<ProjectCardLeak type="leak" measures={MEASURES} project={PROJECT} />); + expect(card.find('.project-card-dates').exists()).toBeTruthy(); + expect(card.find('.project-card-dates').find('span').getNodes()).toHaveLength(2); +}); + +it('should not display analysis date or leak start date', () => { + const project = { ...PROJECT, analysisDate: undefined }; + const card = shallow(<ProjectCardLeak type="leak" measures={MEASURES} project={project} />); + expect(card.find('.project-card-dates').exists()).toBeFalsy(); +}); + +it('should display loading', () => { + const measures = { ...MEASURES, new_bugs: undefined }; + expect( + shallow(<ProjectCardLeak type="leak" measures={measures} project={PROJECT} />) + .find('.boxed-group') + .hasClass('boxed-group-loading') + ).toBeTruthy(); +}); + +it('should display tags', () => { + const project = { ...PROJECT, tags: ['foo', 'bar'] }; + expect( + shallow(<ProjectCardLeak type="leak" project={project} />).find('TagsList').exists() + ).toBeTruthy(); +}); + +it('should private badge', () => { + const project = { ...PROJECT, visibility: 'private' }; + expect( + shallow(<ProjectCardLeak type="leak" project={project} />).find('PrivateBadge').exists() + ).toBeTruthy(); +}); + +it('should display the leak measures and quality gate', () => { + expect( + shallow(<ProjectCardLeak type="leak" measures={MEASURES} project={PROJECT} />) + ).toMatchSnapshot(); +}); diff --git a/server/sonar-web/src/main/js/apps/projects/components/__tests__/ProjectCardOverall-test.js b/server/sonar-web/src/main/js/apps/projects/components/__tests__/ProjectCardOverall-test.js new file mode 100644 index 00000000000..b6f5698f231 --- /dev/null +++ b/server/sonar-web/src/main/js/apps/projects/components/__tests__/ProjectCardOverall-test.js @@ -0,0 +1,93 @@ +/* + * SonarQube + * Copyright (C) 2009-2017 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 React from 'react'; +import { shallow } from 'enzyme'; +import ProjectCardOverall from '../ProjectCardOverall'; + +const PROJECT = { + analysisDate: '2017-01-01', + leakPeriodDate: '2016-12-01', + key: 'foo', + name: 'Foo', + tags: [] +}; +const MEASURES = { + alert_status: 'OK', + reliability_rating: '1.0', + sqale_rating: '1.0', + new_bugs: 12 +}; + +jest.mock('moment', () => () => ({ + format: () => 'March 1, 2017 9:36 AM', + fromNow: () => 'a month ago' +})); + +it('should display analysis date (and not leak period) when defined', () => { + expect( + shallow(<ProjectCardOverall measures={{}} project={PROJECT} />) + .find('.project-card-dates') + .exists() + ).toBeTruthy(); + expect( + shallow(<ProjectCardOverall measures={{}} project={{ ...PROJECT, analysisDate: undefined }} />) + .find('.project-card-dates') + .exists() + ).toBeFalsy(); +}); + +it('should display loading', () => { + const measures = { ...MEASURES, sqale_rating: undefined }; + expect( + shallow(<ProjectCardOverall project={PROJECT} />) + .find('.boxed-group') + .hasClass('boxed-group-loading') + ).toBeTruthy(); + expect( + shallow(<ProjectCardOverall measures={measures} project={PROJECT} />) + .find('.boxed-group') + .hasClass('boxed-group-loading') + ).toBeTruthy(); +}); + +it('should not display the quality gate', () => { + const project = { ...PROJECT, analysisDate: undefined }; + expect( + shallow(<ProjectCardOverall measures={MEASURES} project={project} />) + .find('ProjectCardOverallQualityGate') + .exists() + ).toBeFalsy(); +}); + +it('should display tags', () => { + const project = { ...PROJECT, tags: ['foo', 'bar'] }; + expect(shallow(<ProjectCardOverall project={project} />).find('TagsList').exists()).toBeTruthy(); +}); + +it('should private badge', () => { + const project = { ...PROJECT, visibility: 'private' }; + expect( + shallow(<ProjectCardOverall type="overall" project={project} />).find('PrivateBadge').exists() + ).toBeTruthy(); +}); + +it('should display the overall measures and quality gate', () => { + expect(shallow(<ProjectCardOverall measures={MEASURES} project={PROJECT} />)).toMatchSnapshot(); +}); diff --git a/server/sonar-web/src/main/js/apps/projects/components/__tests__/__snapshots__/ProjectCard-test.js.snap b/server/sonar-web/src/main/js/apps/projects/components/__tests__/__snapshots__/ProjectCard-test.js.snap deleted file mode 100644 index 322b86b25af..00000000000 --- a/server/sonar-web/src/main/js/apps/projects/components/__tests__/__snapshots__/ProjectCard-test.js.snap +++ /dev/null @@ -1,122 +0,0 @@ -// Jest Snapshot v1, https://goo.gl/fbAQLP - -exports[`leak project card should display the leak measures and quality gate 1`] = ` -<div - className="boxed-group project-card" - data-key="foo" -> - <div - className="boxed-group-header clearfix" - > - <h2 - className="project-card-name" - > - <Link - onlyActiveOnIndex={false} - style={Object {}} - to={ - Object { - "pathname": "/dashboard", - "query": Object { - "id": "foo", - }, - } - } - > - Foo - </Link> - </h2> - <ProjectCardQualityGate - status="OK" - /> - <div - className="pull-right text-right" - /> - <div - className="project-card-dates note text-right pull-right" - > - <span> - projects.leak_period_x.a month ago - </span> - <span - className="big-spacer-left" - > - projects.last_analysis_on_x.March 1, 2017 9:36 AM - </span> - </div> - </div> - <div - className="boxed-group-inner" - > - <ProjectCardLeakMeasures - measures={ - Object { - "alert_status": "OK", - "new_bugs": 12, - "reliability_rating": "1.0", - "sqale_rating": "1.0", - } - } - /> - </div> -</div> -`; - -exports[`overall status project card should display the overall measures and quality gate 1`] = ` -<div - className="boxed-group project-card" - data-key="foo" -> - <div - className="boxed-group-header clearfix" - > - <h2 - className="project-card-name" - > - <Link - onlyActiveOnIndex={false} - style={Object {}} - to={ - Object { - "pathname": "/dashboard", - "query": Object { - "id": "foo", - }, - } - } - > - Foo - </Link> - </h2> - <ProjectCardQualityGate - status="OK" - /> - <div - className="pull-right text-right" - /> - <div - className="project-card-dates note text-right pull-right" - > - <span - className="big-spacer-left" - > - projects.last_analysis_on_x.March 1, 2017 9:36 AM - </span> - </div> - </div> - <div - className="boxed-group-inner" - > - <ProjectCardOverallMeasures - measures={ - Object { - "alert_status": "OK", - "new_bugs": 12, - "reliability_rating": "1.0", - "sqale_rating": "1.0", - } - } - /> - </div> -</div> -`; diff --git a/server/sonar-web/src/main/js/apps/projects/components/__tests__/__snapshots__/ProjectCardLeak-test.js.snap b/server/sonar-web/src/main/js/apps/projects/components/__tests__/__snapshots__/ProjectCardLeak-test.js.snap new file mode 100644 index 00000000000..101ba723485 --- /dev/null +++ b/server/sonar-web/src/main/js/apps/projects/components/__tests__/__snapshots__/ProjectCardLeak-test.js.snap @@ -0,0 +1,63 @@ +// Jest Snapshot v1, https://goo.gl/fbAQLP + +exports[`should display the leak measures and quality gate 1`] = ` +<div + className="boxed-group project-card" + data-key="foo" +> + <div + className="boxed-group-header clearfix" + > + <h2 + className="project-card-name" + > + <Link + onlyActiveOnIndex={false} + style={Object {}} + to={ + Object { + "pathname": "/dashboard", + "query": Object { + "id": "foo", + }, + } + } + > + Foo + </Link> + </h2> + <ProjectCardQualityGate + status="OK" + /> + <div + className="pull-right text-right" + /> + <div + className="project-card-dates note text-right pull-right" + > + <span> + projects.leak_period_x.a month ago + </span> + <span + className="big-spacer-left" + > + projects.last_analysis_on_x.March 1, 2017 9:36 AM + </span> + </div> + </div> + <div + className="boxed-group-inner" + > + <ProjectCardLeakMeasures + measures={ + Object { + "alert_status": "OK", + "new_bugs": 12, + "reliability_rating": "1.0", + "sqale_rating": "1.0", + } + } + /> + </div> +</div> +`; diff --git a/server/sonar-web/src/main/js/apps/projects/components/__tests__/__snapshots__/ProjectCardOverall-test.js.snap b/server/sonar-web/src/main/js/apps/projects/components/__tests__/__snapshots__/ProjectCardOverall-test.js.snap new file mode 100644 index 00000000000..1e666cc1854 --- /dev/null +++ b/server/sonar-web/src/main/js/apps/projects/components/__tests__/__snapshots__/ProjectCardOverall-test.js.snap @@ -0,0 +1,60 @@ +// Jest Snapshot v1, https://goo.gl/fbAQLP + +exports[`should display the overall measures and quality gate 1`] = ` +<div + className="boxed-group project-card" + data-key="foo" +> + <div + className="boxed-group-header clearfix" + > + <h2 + className="project-card-name" + > + <Link + onlyActiveOnIndex={false} + style={Object {}} + to={ + Object { + "pathname": "/dashboard", + "query": Object { + "id": "foo", + }, + } + } + > + Foo + </Link> + </h2> + <ProjectCardQualityGate + status="OK" + /> + <div + className="pull-right text-right" + /> + <div + className="project-card-dates note text-right pull-right" + > + <span + className="big-spacer-left" + > + projects.last_analysis_on_x.March 1, 2017 9:36 AM + </span> + </div> + </div> + <div + className="boxed-group-inner" + > + <ProjectCardOverallMeasures + measures={ + Object { + "alert_status": "OK", + "new_bugs": 12, + "reliability_rating": "1.0", + "sqale_rating": "1.0", + } + } + /> + </div> +</div> +`; diff --git a/sonar-core/src/main/resources/org/sonar/l10n/core.properties b/sonar-core/src/main/resources/org/sonar/l10n/core.properties index 7d1f3bb714c..5a4ca39c975 100644 --- a/sonar-core/src/main/resources/org/sonar/l10n/core.properties +++ b/sonar-core/src/main/resources/org/sonar/l10n/core.properties @@ -860,6 +860,7 @@ projects.no_favorite_projects=You don't have any favorite projects yet. projects.no_favorite_projects.engagement=Discover and mark as favorites projects you are interested in to have a quick access to them. projects.explore_projects=Explore Projects projects.not_analyzed=Project is not analyzed yet. +projects.no_leak_period=Project has no leak data yet. projects.leak_period_x=Leak Period started {0} projects.last_analysis_on_x=Last analysis on {0} projects.search=Search by project name or key |