Skip to content

Commit 177688d

Browse files
authored
Merge pull request #1544 from github/koesie10/scanned-repos-tab
Add analyzed repositories component
2 parents c5cbf92 + f8cc3ae commit 177688d

14 files changed

+902
-18
lines changed

extensions/ql-vscode/src/remote-queries/shared/variant-analysis.ts

Lines changed: 19 additions & 4 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,5 @@
11
import { Repository } from './repository';
2+
import { AnalysisAlert, AnalysisRawResults } from './analysis-result';
23

34
export interface VariantAnalysis {
45
id: number,
@@ -78,6 +79,12 @@ export interface VariantAnalysisSkippedRepositoryGroup {
7879
}>
7980
}
8081

82+
export interface VariantAnalysisScannedRepositoryResult {
83+
repositoryId: number;
84+
interpretedResults?: AnalysisAlert[];
85+
rawResults?: AnalysisRawResults;
86+
}
87+
8188
/**
8289
* Captures information needed to submit a variant
8390
* analysis for processing.
@@ -102,16 +109,24 @@ export interface VariantAnalysisSubmission {
102109
}
103110

104111
/**
105-
* @param repo
106-
* @returns whether the repo scan is in a completed state, i.e. it cannot normally change state anymore
112+
* @param status
113+
* @returns whether the status is in a completed state, i.e. it cannot normally change state anymore
107114
*/
108-
export function hasRepoScanCompleted(repo: VariantAnalysisScannedRepository): boolean {
115+
export function isCompletedAnalysisRepoStatus(status: VariantAnalysisRepoStatus): boolean {
109116
return [
110117
// All states that indicates the repository has been scanned and cannot
111118
// change status anymore.
112119
VariantAnalysisRepoStatus.Succeeded, VariantAnalysisRepoStatus.Failed,
113120
VariantAnalysisRepoStatus.Canceled, VariantAnalysisRepoStatus.TimedOut,
114-
].includes(repo.analysisStatus);
121+
].includes(status);
122+
}
123+
124+
/**
125+
* @param repo
126+
* @returns whether the repo scan is in a completed state, i.e. it cannot normally change state anymore
127+
*/
128+
export function hasRepoScanCompleted(repo: VariantAnalysisScannedRepository): boolean {
129+
return isCompletedAnalysisRepoStatus(repo.analysisStatus);
115130
}
116131

117132
/**

extensions/ql-vscode/src/stories/remote-queries/data/rawResults.json

Lines changed: 26 additions & 0 deletions
Some generated files are not rendered by default. Learn more about customizing how changed files appear on GitHub.
Lines changed: 79 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,79 @@
1+
import React from 'react';
2+
3+
import { ComponentMeta, ComponentStory } from '@storybook/react';
4+
5+
import { VariantAnalysisContainer } from '../../view/variant-analysis/VariantAnalysisContainer';
6+
import { VariantAnalysisAnalyzedRepoItem } from '../../view/variant-analysis/VariantAnalysisAnalyzedRepoItem';
7+
import { VariantAnalysisRepoStatus } from '../../remote-queries/shared/variant-analysis';
8+
import { AnalysisAlert, AnalysisRawResults } from '../../remote-queries/shared/analysis-result';
9+
10+
import analysesResults from '../remote-queries/data/analysesResultsMessage.json';
11+
import rawResults from '../remote-queries/data/rawResults.json';
12+
13+
export default {
14+
title: 'Variant Analysis/Analyzed Repo Item',
15+
component: VariantAnalysisAnalyzedRepoItem,
16+
decorators: [
17+
(Story) => (
18+
<VariantAnalysisContainer>
19+
<Story />
20+
</VariantAnalysisContainer>
21+
)
22+
],
23+
} as ComponentMeta<typeof VariantAnalysisAnalyzedRepoItem>;
24+
25+
const Template: ComponentStory<typeof VariantAnalysisAnalyzedRepoItem> = (args) => (
26+
<VariantAnalysisAnalyzedRepoItem {...args} />
27+
);
28+
29+
export const Pending = Template.bind({});
30+
Pending.args = {
31+
repository: {
32+
id: 63537249,
33+
fullName: 'facebook/create-react-app',
34+
private: false,
35+
},
36+
status: VariantAnalysisRepoStatus.Pending,
37+
};
38+
39+
export const InProgress = Template.bind({});
40+
InProgress.args = {
41+
...Pending.args,
42+
status: VariantAnalysisRepoStatus.InProgress,
43+
interpretedResults: undefined,
44+
};
45+
46+
export const Failed = Template.bind({});
47+
Failed.args = {
48+
...Pending.args,
49+
status: VariantAnalysisRepoStatus.Failed,
50+
interpretedResults: undefined,
51+
};
52+
53+
export const TimedOut = Template.bind({});
54+
TimedOut.args = {
55+
...Pending.args,
56+
status: VariantAnalysisRepoStatus.TimedOut,
57+
};
58+
59+
export const Canceled = Template.bind({});
60+
Canceled.args = {
61+
...Pending.args,
62+
status: VariantAnalysisRepoStatus.Canceled,
63+
};
64+
65+
export const InterpretedResults = Template.bind({});
66+
InterpretedResults.args = {
67+
...Pending.args,
68+
status: VariantAnalysisRepoStatus.Succeeded,
69+
resultCount: 198,
70+
interpretedResults: analysesResults.analysesResults.find(v => v.nwo === 'facebook/create-react-app')?.interpretedResults as unknown as AnalysisAlert[],
71+
};
72+
73+
export const RawResults = Template.bind({});
74+
RawResults.args = {
75+
...InterpretedResults.args,
76+
interpretedResults: undefined,
77+
resultCount: 1,
78+
rawResults: rawResults as unknown as AnalysisRawResults,
79+
};
Lines changed: 116 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,116 @@
1+
import React from 'react';
2+
3+
import { ComponentMeta, ComponentStory } from '@storybook/react';
4+
5+
import { VariantAnalysisContainer } from '../../view/variant-analysis/VariantAnalysisContainer';
6+
import { VariantAnalysisAnalyzedRepos } from '../../view/variant-analysis/VariantAnalysisAnalyzedRepos';
7+
import {
8+
VariantAnalysisQueryLanguage,
9+
VariantAnalysisRepoStatus,
10+
VariantAnalysisStatus
11+
} from '../../remote-queries/shared/variant-analysis';
12+
import { AnalysisAlert } from '../../remote-queries/shared/analysis-result';
13+
14+
import analysesResults from '../remote-queries/data/analysesResultsMessage.json';
15+
16+
export default {
17+
title: 'Variant Analysis/Analyzed Repos',
18+
component: VariantAnalysisAnalyzedRepos,
19+
decorators: [
20+
(Story) => (
21+
<VariantAnalysisContainer>
22+
<Story />
23+
</VariantAnalysisContainer>
24+
)
25+
],
26+
} as ComponentMeta<typeof VariantAnalysisAnalyzedRepos>;
27+
28+
const Template: ComponentStory<typeof VariantAnalysisAnalyzedRepos> = (args) => (
29+
<VariantAnalysisAnalyzedRepos {...args} />
30+
);
31+
32+
const interpretedResultsForRepo = (nwo: string): AnalysisAlert[] | undefined => {
33+
return analysesResults.analysesResults.find(v => v.nwo === nwo)?.interpretedResults as unknown as AnalysisAlert[];
34+
};
35+
36+
export const Example = Template.bind({});
37+
Example.args = {
38+
variantAnalysis: {
39+
id: 1,
40+
controllerRepoId: 1,
41+
query: {
42+
name: 'Query name',
43+
filePath: 'example.ql',
44+
language: VariantAnalysisQueryLanguage.Javascript,
45+
},
46+
databases: {},
47+
status: VariantAnalysisStatus.InProgress,
48+
scannedRepos: [
49+
{
50+
repository: {
51+
id: 63537249,
52+
fullName: 'facebook/create-react-app',
53+
private: false,
54+
},
55+
analysisStatus: VariantAnalysisRepoStatus.Succeeded, resultCount: 198,
56+
},
57+
{
58+
repository: {
59+
id: 167174,
60+
fullName: 'jquery/jquery',
61+
private: false,
62+
},
63+
analysisStatus: VariantAnalysisRepoStatus.Succeeded,
64+
resultCount: 67,
65+
},
66+
{
67+
repository: {
68+
id: 237159,
69+
fullName: 'expressjs/express',
70+
private: false,
71+
},
72+
analysisStatus: VariantAnalysisRepoStatus.Succeeded,
73+
resultCount: 26,
74+
},
75+
{
76+
repository: {
77+
id: 15062869,
78+
fullName: 'facebook/jest',
79+
private: false,
80+
},
81+
analysisStatus: VariantAnalysisRepoStatus.Failed,
82+
},
83+
{
84+
repository: {
85+
id: 24195339,
86+
fullName: 'angular/angular',
87+
private: false,
88+
},
89+
analysisStatus: VariantAnalysisRepoStatus.InProgress,
90+
},
91+
{
92+
repository: {
93+
id: 24560307,
94+
fullName: 'babel/babel',
95+
private: false,
96+
},
97+
analysisStatus: VariantAnalysisRepoStatus.Pending,
98+
},
99+
]
100+
},
101+
repositoryResults: [
102+
{
103+
repositoryId: 63537249,
104+
interpretedResults: interpretedResultsForRepo('facebook/create-react-app'),
105+
},
106+
{
107+
repositoryId: 167174,
108+
interpretedResults: interpretedResultsForRepo('jquery/jquery'),
109+
},
110+
{
111+
repositoryId: 237159,
112+
interpretedResults: interpretedResultsForRepo('expressjs/express'),
113+
}
114+
]
115+
}
116+
;
Lines changed: 13 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,13 @@
1+
import * as React from 'react';
2+
import { Codicon } from './Codicon';
3+
import classNames from 'classnames';
4+
5+
type Props = {
6+
label?: string;
7+
className?: string;
8+
}
9+
10+
export const LoadingIcon = ({
11+
label = 'Loading...',
12+
className,
13+
}: Props) => <Codicon name="loading" label={label} className={classNames(className, 'codicon-modifier-spin')} />;
Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,5 @@
11
export * from './Codicon';
22
export * from './ErrorIcon';
3+
export * from './LoadingIcon';
34
export * from './SuccessIcon';
45
export * from './WarningIcon';
Lines changed: 88 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,88 @@
1+
import * as React from 'react';
2+
import styled from 'styled-components';
3+
import { AnalysisAlert, AnalysisRawResults } from '../../remote-queries/shared/analysis-result';
4+
import AnalysisAlertResult from '../remote-queries/AnalysisAlertResult';
5+
import RawResultsTable from '../remote-queries/RawResultsTable';
6+
import { VariantAnalysisRepoStatus } from '../../remote-queries/shared/variant-analysis';
7+
import { Alert } from '../common';
8+
9+
const ContentContainer = styled.div`
10+
display: flex;
11+
flex-direction: column;
12+
`;
13+
14+
const AlertContainer = styled.div`
15+
margin-top: 1em;
16+
`;
17+
18+
const InterpretedResultsContainer = styled.ul`
19+
list-style-type: none;
20+
margin: 1em 0 0;
21+
padding: 0.5em 0 0 0;
22+
`;
23+
24+
const InterpretedResultItem = styled.li`
25+
margin-bottom: 1em;
26+
background-color: var(--vscode-notifications-background);
27+
`;
28+
29+
const RawResultsContainer = styled.div`
30+
display: block;
31+
margin-top: 0.5em;
32+
`;
33+
34+
export type AnalyzedRepoItemContentProps = {
35+
status: VariantAnalysisRepoStatus;
36+
37+
interpretedResults?: AnalysisAlert[];
38+
rawResults?: AnalysisRawResults;
39+
}
40+
41+
export const AnalyzedRepoItemContent = ({
42+
status,
43+
interpretedResults,
44+
rawResults,
45+
}: AnalyzedRepoItemContentProps) => {
46+
return (
47+
<ContentContainer>
48+
{status === VariantAnalysisRepoStatus.Failed && <AlertContainer>
49+
<Alert
50+
type="error"
51+
title="Failed"
52+
message="The query failed to run on this repository."
53+
/>
54+
</AlertContainer>}
55+
{status === VariantAnalysisRepoStatus.TimedOut && <AlertContainer>
56+
<Alert
57+
type="error"
58+
title="Timed out"
59+
message="The analysis ran out of time and we couldn't scan the repository."
60+
/>
61+
</AlertContainer>}
62+
{status === VariantAnalysisRepoStatus.Canceled && <AlertContainer>
63+
<Alert
64+
type="error"
65+
title="Canceled"
66+
message="The variant analysis or this repository was canceled."
67+
/>
68+
</AlertContainer>}
69+
{interpretedResults && (
70+
<InterpretedResultsContainer>
71+
{interpretedResults.map((r, i) =>
72+
<InterpretedResultItem key={i}>
73+
<AnalysisAlertResult alert={r} />
74+
</InterpretedResultItem>)}
75+
</InterpretedResultsContainer>
76+
)}
77+
{rawResults && (
78+
<RawResultsContainer>
79+
<RawResultsTable
80+
schema={rawResults.schema}
81+
results={rawResults.resultSet}
82+
fileLinkPrefix={rawResults.fileLinkPrefix}
83+
sourceLocationPrefix={rawResults.sourceLocationPrefix} />
84+
</RawResultsContainer>
85+
)}
86+
</ContentContainer>
87+
);
88+
};

0 commit comments

Comments
 (0)